aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/net
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/net')
-rw-r--r--drivers/net/can/flexcan.c6
-rw-r--r--drivers/net/can/sja1000/Kconfig2
-rw-r--r--drivers/net/ethernet/3com/typhoon.c3
-rw-r--r--drivers/net/ethernet/amd/ariadne.c8
-rw-r--r--drivers/net/ethernet/amd/atarilance.c11
-rw-r--r--drivers/net/ethernet/broadcom/tg3.c3
-rw-r--r--drivers/net/ethernet/brocade/bna/bnad.c4
-rw-r--r--drivers/net/ethernet/chelsio/cxgb4/cxgb4.h23
-rw-r--r--drivers/net/ethernet/chelsio/cxgb4/cxgb4_main.c235
-rw-r--r--drivers/net/ethernet/chelsio/cxgb4/cxgb4_uld.h11
-rw-r--r--drivers/net/ethernet/chelsio/cxgb4/sge.c22
-rw-r--r--drivers/net/ethernet/chelsio/cxgb4/t4_hw.c62
-rw-r--r--drivers/net/ethernet/chelsio/cxgb4/t4_regs.h53
-rw-r--r--drivers/net/ethernet/chelsio/cxgb4/t4fw_api.h15
-rw-r--r--drivers/net/ethernet/emulex/benet/Makefile2
-rw-r--r--drivers/net/ethernet/emulex/benet/be.h37
-rw-r--r--drivers/net/ethernet/emulex/benet/be_cmds.c39
-rw-r--r--drivers/net/ethernet/emulex/benet/be_cmds.h1
-rw-r--r--drivers/net/ethernet/emulex/benet/be_hw.h4
-rw-r--r--drivers/net/ethernet/emulex/benet/be_main.c88
-rw-r--r--drivers/net/ethernet/emulex/benet/be_roce.c182
-rw-r--r--drivers/net/ethernet/emulex/benet/be_roce.h75
-rw-r--r--drivers/net/ethernet/freescale/fec.c9
-rw-r--r--drivers/net/ethernet/mellanox/mlx4/alloc.c3
-rw-r--r--drivers/net/ethernet/mellanox/mlx4/fw.c29
-rw-r--r--drivers/net/ethernet/mellanox/mlx4/fw.h2
-rw-r--r--drivers/net/ethernet/mellanox/mlx4/main.c2
-rw-r--r--drivers/net/ethernet/nxp/lpc_eth.c71
-rw-r--r--drivers/net/ethernet/qlogic/netxen/netxen_nic_init.c3
-rw-r--r--drivers/net/ethernet/qlogic/qlcnic/qlcnic_init.c3
-rw-r--r--drivers/net/ethernet/realtek/r8169.c2
-rw-r--r--drivers/net/ethernet/s6gmac.c4
-rw-r--r--drivers/net/ethernet/tehuti/tehuti.c4
-rw-r--r--drivers/net/irda/Kconfig6
-rw-r--r--drivers/net/irda/irda-usb.c2
-rw-r--r--drivers/net/irda/kingsun-sir.c42
-rw-r--r--drivers/net/irda/ks959-sir.c31
-rw-r--r--drivers/net/irda/ksdazzle-sir.c46
-rw-r--r--drivers/net/irda/stir4200.c6
-rw-r--r--drivers/net/usb/asix.c1
-rw-r--r--drivers/net/usb/catc.c26
-rw-r--r--drivers/net/usb/cdc-phonet.c1
-rw-r--r--drivers/net/usb/cdc_eem.c1
-rw-r--r--drivers/net/usb/cdc_ether.c1
-rw-r--r--drivers/net/usb/cdc_ncm.c1
-rw-r--r--drivers/net/usb/cdc_subset.c1
-rw-r--r--drivers/net/usb/cx82310_eth.c1
-rw-r--r--drivers/net/usb/dm9601.c1
-rw-r--r--drivers/net/usb/gl620a.c1
-rw-r--r--drivers/net/usb/hso.c106
-rw-r--r--drivers/net/usb/int51x1.c1
-rw-r--r--drivers/net/usb/ipheth.c35
-rw-r--r--drivers/net/usb/kalmia.c3
-rw-r--r--drivers/net/usb/kaweth.c64
-rw-r--r--drivers/net/usb/lg-vl600.c1
-rw-r--r--drivers/net/usb/mcs7830.c1
-rw-r--r--drivers/net/usb/net1080.c1
-rw-r--r--drivers/net/usb/pegasus.c1
-rw-r--r--drivers/net/usb/plusb.c1
-rw-r--r--drivers/net/usb/qmi_wwan.c1
-rw-r--r--drivers/net/usb/rndis_host.c1
-rw-r--r--drivers/net/usb/rtl8150.c18
-rw-r--r--drivers/net/usb/sierra_net.c1
-rw-r--r--drivers/net/usb/smsc75xx.c1
-rw-r--r--drivers/net/usb/smsc95xx.c1
-rw-r--r--drivers/net/usb/zaurus.c1
-rw-r--r--drivers/net/wan/Kconfig31
-rw-r--r--drivers/net/wan/Makefile5
-rw-r--r--drivers/net/wan/pc300-falc-lh.h1238
-rw-r--r--drivers/net/wan/pc300.h436
-rw-r--r--drivers/net/wan/pc300_drv.c3670
-rw-r--r--drivers/net/wan/pc300_tty.c1079
-rw-r--r--drivers/net/wireless/at76c50x-usb.c3
-rw-r--r--drivers/net/wireless/ath/ath6kl/usb.c1
-rw-r--r--drivers/net/wireless/ath/ath9k/hif_usb.c1
-rw-r--r--drivers/net/wireless/ath/carl9170/usb.c1
-rw-r--r--drivers/net/wireless/brcm80211/brcmfmac/usb.c3
-rw-r--r--drivers/net/wireless/libertas/if_usb.c1
-rw-r--r--drivers/net/wireless/libertas_tf/if_usb.c1
-rw-r--r--drivers/net/wireless/orinoco/orinoco_usb.c1
-rw-r--r--drivers/net/wireless/p54/p54usb.c1
-rw-r--r--drivers/net/wireless/rndis_wlan.c1
-rw-r--r--drivers/net/wireless/rt2x00/rt2500usb.c1
-rw-r--r--drivers/net/wireless/rt2x00/rt2800usb.c1
-rw-r--r--drivers/net/wireless/rt2x00/rt73usb.c1
-rw-r--r--drivers/net/wireless/rtl818x/rtl8187/dev.c1
-rw-r--r--drivers/net/wireless/rtlwifi/rtl8192cu/sw.c1
-rw-r--r--drivers/net/wireless/zd1201.c1
-rw-r--r--drivers/net/wireless/zd1211rw/zd_usb.c1
89 files changed, 1189 insertions, 6715 deletions
diff --git a/drivers/net/can/flexcan.c b/drivers/net/can/flexcan.c
index 1efb08386c61..38c0690df5c8 100644
--- a/drivers/net/can/flexcan.c
+++ b/drivers/net/can/flexcan.c
@@ -35,6 +35,7 @@
#include <linux/module.h>
#include <linux/of.h>
#include <linux/platform_device.h>
+#include <linux/pinctrl/consumer.h>
#define DRV_NAME "flexcan"
@@ -927,11 +928,16 @@ static int __devinit flexcan_probe(struct platform_device *pdev)
struct flexcan_priv *priv;
struct resource *mem;
struct clk *clk = NULL;
+ struct pinctrl *pinctrl;
void __iomem *base;
resource_size_t mem_size;
int err, irq;
u32 clock_freq = 0;
+ pinctrl = devm_pinctrl_get_select_default(&pdev->dev);
+ if (IS_ERR(pinctrl))
+ return PTR_ERR(pinctrl);
+
if (pdev->dev.of_node) {
const u32 *clock_freq_p;
diff --git a/drivers/net/can/sja1000/Kconfig b/drivers/net/can/sja1000/Kconfig
index b60d6c5f29a0..03df9a8f2bbf 100644
--- a/drivers/net/can/sja1000/Kconfig
+++ b/drivers/net/can/sja1000/Kconfig
@@ -75,7 +75,7 @@ config CAN_KVASER_PCI
tristate "Kvaser PCIcanx and Kvaser PCIcan PCI Cards"
depends on PCI
---help---
- This driver is for the the PCIcanx and PCIcan cards (1, 2 or
+ This driver is for the PCIcanx and PCIcan cards (1, 2 or
4 channel) from Kvaser (http://www.kvaser.com).
config CAN_PLX_PCI
diff --git a/drivers/net/ethernet/3com/typhoon.c b/drivers/net/ethernet/3com/typhoon.c
index 1234a14b2b73..b15366635147 100644
--- a/drivers/net/ethernet/3com/typhoon.c
+++ b/drivers/net/ethernet/3com/typhoon.c
@@ -2549,8 +2549,7 @@ typhoon_init(void)
static void __exit
typhoon_cleanup(void)
{
- if (typhoon_fw)
- release_firmware(typhoon_fw);
+ release_firmware(typhoon_fw);
pci_unregister_driver(&typhoon_driver);
}
diff --git a/drivers/net/ethernet/amd/ariadne.c b/drivers/net/ethernet/amd/ariadne.c
index f4c228e4d76c..f2958df9a1e4 100644
--- a/drivers/net/ethernet/amd/ariadne.c
+++ b/drivers/net/ethernet/amd/ariadne.c
@@ -213,10 +213,10 @@ static int ariadne_rx(struct net_device *dev)
(const void *)priv->rx_buff[entry],
pkt_len);
skb->protocol = eth_type_trans(skb, dev);
- netdev_dbg(dev, "RX pkt type 0x%04x from %pM to %pM data 0x%08x len %d\n",
+ netdev_dbg(dev, "RX pkt type 0x%04x from %pM to %pM data %p len %u\n",
((u_short *)skb->data)[6],
skb->data + 6, skb->data,
- (int)skb->data, (int)skb->len);
+ skb->data, skb->len);
netif_rx(skb);
dev->stats.rx_packets++;
@@ -566,10 +566,10 @@ static netdev_tx_t ariadne_start_xmit(struct sk_buff *skb,
/* Fill in a Tx ring entry */
- netdev_dbg(dev, "TX pkt type 0x%04x from %pM to %pM data 0x%08x len %d\n",
+ netdev_dbg(dev, "TX pkt type 0x%04x from %pM to %pM data %p len %u\n",
((u_short *)skb->data)[6],
skb->data + 6, skb->data,
- (int)skb->data, (int)skb->len);
+ skb->data, skb->len);
local_irq_save(flags);
diff --git a/drivers/net/ethernet/amd/atarilance.c b/drivers/net/ethernet/amd/atarilance.c
index 70ed79c46245..84219df72f51 100644
--- a/drivers/net/ethernet/amd/atarilance.c
+++ b/drivers/net/ethernet/amd/atarilance.c
@@ -558,21 +558,18 @@ static unsigned long __init lance_probe1( struct net_device *dev,
printk( "Lance: request for irq %d failed\n", IRQ_AUTO_5 );
return 0;
}
- dev->irq = (unsigned short)IRQ_AUTO_5;
+ dev->irq = IRQ_AUTO_5;
}
else {
- /* For VME-RieblCards, request a free VME int;
- * (This must be unsigned long, since dev->irq is short and the
- * IRQ_MACHSPEC bit would be cut off...)
- */
- unsigned long irq = atari_register_vme_int();
+ /* For VME-RieblCards, request a free VME int */
+ unsigned int irq = atari_register_vme_int();
if (!irq) {
printk( "Lance: request for VME interrupt failed\n" );
return 0;
}
if (request_irq(irq, lance_interrupt, IRQ_TYPE_PRIO,
"Riebl-VME Ethernet", dev)) {
- printk( "Lance: request for irq %ld failed\n", irq );
+ printk( "Lance: request for irq %u failed\n", irq );
return 0;
}
dev->irq = irq;
diff --git a/drivers/net/ethernet/broadcom/tg3.c b/drivers/net/ethernet/broadcom/tg3.c
index d55df3290174..edeeb516807a 100644
--- a/drivers/net/ethernet/broadcom/tg3.c
+++ b/drivers/net/ethernet/broadcom/tg3.c
@@ -15883,8 +15883,7 @@ static void __devexit tg3_remove_one(struct pci_dev *pdev)
if (dev) {
struct tg3 *tp = netdev_priv(dev);
- if (tp->fw)
- release_firmware(tp->fw);
+ release_firmware(tp->fw);
tg3_reset_task_cancel(tp);
diff --git a/drivers/net/ethernet/brocade/bna/bnad.c b/drivers/net/ethernet/brocade/bna/bnad.c
index 25c4e7f2a099..67cd2ed0306a 100644
--- a/drivers/net/ethernet/brocade/bna/bnad.c
+++ b/drivers/net/ethernet/brocade/bna/bnad.c
@@ -3520,9 +3520,7 @@ static void __exit
bnad_module_exit(void)
{
pci_unregister_driver(&bnad_pci_driver);
-
- if (bfi_fw)
- release_firmware(bfi_fw);
+ release_firmware(bfi_fw);
}
module_init(bnad_module_init);
diff --git a/drivers/net/ethernet/chelsio/cxgb4/cxgb4.h b/drivers/net/ethernet/chelsio/cxgb4/cxgb4.h
index 0fe18850c838..ec2dafe8ae5b 100644
--- a/drivers/net/ethernet/chelsio/cxgb4/cxgb4.h
+++ b/drivers/net/ethernet/chelsio/cxgb4/cxgb4.h
@@ -51,6 +51,8 @@
#define FW_VERSION_MINOR 1
#define FW_VERSION_MICRO 0
+#define CH_WARN(adap, fmt, ...) dev_warn(adap->pdev_dev, fmt, ## __VA_ARGS__)
+
enum {
MAX_NPORTS = 4, /* max # of ports */
SERNUM_LEN = 24, /* Serial # length */
@@ -64,6 +66,15 @@ enum {
MEM_MC
};
+enum {
+ MEMWIN0_APERTURE = 65536,
+ MEMWIN0_BASE = 0x30000,
+ MEMWIN1_APERTURE = 32768,
+ MEMWIN1_BASE = 0x28000,
+ MEMWIN2_APERTURE = 2048,
+ MEMWIN2_BASE = 0x1b800,
+};
+
enum dev_master {
MASTER_CANT,
MASTER_MAY,
@@ -403,6 +414,9 @@ struct sge_txq {
struct tx_sw_desc *sdesc; /* address of SW Tx descriptor ring */
struct sge_qstat *stat; /* queue status entry */
dma_addr_t phys_addr; /* physical address of the ring */
+ spinlock_t db_lock;
+ int db_disabled;
+ unsigned short db_pidx;
};
struct sge_eth_txq { /* state for an SGE Ethernet Tx queue */
@@ -475,6 +489,7 @@ struct adapter {
void __iomem *regs;
struct pci_dev *pdev;
struct device *pdev_dev;
+ unsigned int mbox;
unsigned int fn;
unsigned int flags;
@@ -504,6 +519,8 @@ struct adapter {
void **tid_release_head;
spinlock_t tid_release_lock;
struct work_struct tid_release_task;
+ struct work_struct db_full_task;
+ struct work_struct db_drop_task;
bool tid_release_task_busy;
struct dentry *debugfs_root;
@@ -605,6 +622,7 @@ irqreturn_t t4_sge_intr_msix(int irq, void *cookie);
void t4_sge_init(struct adapter *adap);
void t4_sge_start(struct adapter *adap);
void t4_sge_stop(struct adapter *adap);
+extern int dbfifo_int_thresh;
#define for_each_port(adapter, iter) \
for (iter = 0; iter < (adapter)->params.nports; ++iter)
@@ -719,4 +737,9 @@ int t4_ctrl_eq_free(struct adapter *adap, unsigned int mbox, unsigned int pf,
int t4_ofld_eq_free(struct adapter *adap, unsigned int mbox, unsigned int pf,
unsigned int vf, unsigned int eqid);
int t4_handle_fw_rpl(struct adapter *adap, const __be64 *rpl);
+void t4_db_full(struct adapter *adapter);
+void t4_db_dropped(struct adapter *adapter);
+int t4_mem_win_read_len(struct adapter *adap, u32 addr, __be32 *data, int len);
+int t4_fwaddrspace_write(struct adapter *adap, unsigned int mbox,
+ u32 addr, u32 val);
#endif /* __CXGB4_H__ */
diff --git a/drivers/net/ethernet/chelsio/cxgb4/cxgb4_main.c b/drivers/net/ethernet/chelsio/cxgb4/cxgb4_main.c
index b126b98065a9..e1f96fbb48c1 100644
--- a/drivers/net/ethernet/chelsio/cxgb4/cxgb4_main.c
+++ b/drivers/net/ethernet/chelsio/cxgb4/cxgb4_main.c
@@ -149,15 +149,6 @@ static unsigned int pfvfres_pmask(struct adapter *adapter,
#endif
enum {
- MEMWIN0_APERTURE = 65536,
- MEMWIN0_BASE = 0x30000,
- MEMWIN1_APERTURE = 32768,
- MEMWIN1_BASE = 0x28000,
- MEMWIN2_APERTURE = 2048,
- MEMWIN2_BASE = 0x1b800,
-};
-
-enum {
MAX_TXQ_ENTRIES = 16384,
MAX_CTRL_TXQ_ENTRIES = 1024,
MAX_RSPQ_ENTRIES = 16384,
@@ -371,6 +362,15 @@ static int set_addr_filters(const struct net_device *dev, bool sleep)
uhash | mhash, sleep);
}
+int dbfifo_int_thresh = 10; /* 10 == 640 entry threshold */
+module_param(dbfifo_int_thresh, int, 0644);
+MODULE_PARM_DESC(dbfifo_int_thresh, "doorbell fifo interrupt threshold");
+
+int dbfifo_drain_delay = 1000; /* usecs to sleep while draining the dbfifo */
+module_param(dbfifo_drain_delay, int, 0644);
+MODULE_PARM_DESC(dbfifo_drain_delay,
+ "usecs to sleep while draining the dbfifo");
+
/*
* Set Rx properties of a port, such as promiscruity, address filters, and MTU.
* If @mtu is -1 it is left unchanged.
@@ -389,6 +389,8 @@ static int set_rxmode(struct net_device *dev, int mtu, bool sleep_ok)
return ret;
}
+static struct workqueue_struct *workq;
+
/**
* link_start - enable a port
* @dev: the port to enable
@@ -2196,7 +2198,7 @@ static void cxgb4_queue_tid_release(struct tid_info *t, unsigned int chan,
adap->tid_release_head = (void **)((uintptr_t)p | chan);
if (!adap->tid_release_task_busy) {
adap->tid_release_task_busy = true;
- schedule_work(&adap->tid_release_task);
+ queue_work(workq, &adap->tid_release_task);
}
spin_unlock_bh(&adap->tid_release_lock);
}
@@ -2366,6 +2368,16 @@ unsigned int cxgb4_port_chan(const struct net_device *dev)
}
EXPORT_SYMBOL(cxgb4_port_chan);
+unsigned int cxgb4_dbfifo_count(const struct net_device *dev, int lpfifo)
+{
+ struct adapter *adap = netdev2adap(dev);
+ u32 v;
+
+ v = t4_read_reg(adap, A_SGE_DBFIFO_STATUS);
+ return lpfifo ? G_LP_COUNT(v) : G_HP_COUNT(v);
+}
+EXPORT_SYMBOL(cxgb4_dbfifo_count);
+
/**
* cxgb4_port_viid - get the VI id of a port
* @dev: the net device for the port
@@ -2413,6 +2425,59 @@ void cxgb4_iscsi_init(struct net_device *dev, unsigned int tag_mask,
}
EXPORT_SYMBOL(cxgb4_iscsi_init);
+int cxgb4_flush_eq_cache(struct net_device *dev)
+{
+ struct adapter *adap = netdev2adap(dev);
+ int ret;
+
+ ret = t4_fwaddrspace_write(adap, adap->mbox,
+ 0xe1000000 + A_SGE_CTXT_CMD, 0x20000000);
+ return ret;
+}
+EXPORT_SYMBOL(cxgb4_flush_eq_cache);
+
+static int read_eq_indices(struct adapter *adap, u16 qid, u16 *pidx, u16 *cidx)
+{
+ u32 addr = t4_read_reg(adap, A_SGE_DBQ_CTXT_BADDR) + 24 * qid + 8;
+ __be64 indices;
+ int ret;
+
+ ret = t4_mem_win_read_len(adap, addr, (__be32 *)&indices, 8);
+ if (!ret) {
+ indices = be64_to_cpu(indices);
+ *cidx = (indices >> 25) & 0xffff;
+ *pidx = (indices >> 9) & 0xffff;
+ }
+ return ret;
+}
+
+int cxgb4_sync_txq_pidx(struct net_device *dev, u16 qid, u16 pidx,
+ u16 size)
+{
+ struct adapter *adap = netdev2adap(dev);
+ u16 hw_pidx, hw_cidx;
+ int ret;
+
+ ret = read_eq_indices(adap, qid, &hw_pidx, &hw_cidx);
+ if (ret)
+ goto out;
+
+ if (pidx != hw_pidx) {
+ u16 delta;
+
+ if (pidx >= hw_pidx)
+ delta = pidx - hw_pidx;
+ else
+ delta = size - hw_pidx + pidx;
+ wmb();
+ t4_write_reg(adap, MYPF_REG(A_SGE_PF_KDOORBELL),
+ V_QID(qid) | V_PIDX(delta));
+ }
+out:
+ return ret;
+}
+EXPORT_SYMBOL(cxgb4_sync_txq_pidx);
+
static struct pci_driver cxgb4_driver;
static void check_neigh_update(struct neighbour *neigh)
@@ -2446,6 +2511,144 @@ static struct notifier_block cxgb4_netevent_nb = {
.notifier_call = netevent_cb
};
+static void drain_db_fifo(struct adapter *adap, int usecs)
+{
+ u32 v;
+
+ do {
+ set_current_state(TASK_UNINTERRUPTIBLE);
+ schedule_timeout(usecs_to_jiffies(usecs));
+ v = t4_read_reg(adap, A_SGE_DBFIFO_STATUS);
+ if (G_LP_COUNT(v) == 0 && G_HP_COUNT(v) == 0)
+ break;
+ } while (1);
+}
+
+static void disable_txq_db(struct sge_txq *q)
+{
+ spin_lock_irq(&q->db_lock);
+ q->db_disabled = 1;
+ spin_unlock_irq(&q->db_lock);
+}
+
+static void enable_txq_db(struct sge_txq *q)
+{
+ spin_lock_irq(&q->db_lock);
+ q->db_disabled = 0;
+ spin_unlock_irq(&q->db_lock);
+}
+
+static void disable_dbs(struct adapter *adap)
+{
+ int i;
+
+ for_each_ethrxq(&adap->sge, i)
+ disable_txq_db(&adap->sge.ethtxq[i].q);
+ for_each_ofldrxq(&adap->sge, i)
+ disable_txq_db(&adap->sge.ofldtxq[i].q);
+ for_each_port(adap, i)
+ disable_txq_db(&adap->sge.ctrlq[i].q);
+}
+
+static void enable_dbs(struct adapter *adap)
+{
+ int i;
+
+ for_each_ethrxq(&adap->sge, i)
+ enable_txq_db(&adap->sge.ethtxq[i].q);
+ for_each_ofldrxq(&adap->sge, i)
+ enable_txq_db(&adap->sge.ofldtxq[i].q);
+ for_each_port(adap, i)
+ enable_txq_db(&adap->sge.ctrlq[i].q);
+}
+
+static void sync_txq_pidx(struct adapter *adap, struct sge_txq *q)
+{
+ u16 hw_pidx, hw_cidx;
+ int ret;
+
+ spin_lock_bh(&q->db_lock);
+ ret = read_eq_indices(adap, (u16)q->cntxt_id, &hw_pidx, &hw_cidx);
+ if (ret)
+ goto out;
+ if (q->db_pidx != hw_pidx) {
+ u16 delta;
+
+ if (q->db_pidx >= hw_pidx)
+ delta = q->db_pidx - hw_pidx;
+ else
+ delta = q->size - hw_pidx + q->db_pidx;
+ wmb();
+ t4_write_reg(adap, MYPF_REG(A_SGE_PF_KDOORBELL),
+ V_QID(q->cntxt_id) | V_PIDX(delta));
+ }
+out:
+ q->db_disabled = 0;
+ spin_unlock_bh(&q->db_lock);
+ if (ret)
+ CH_WARN(adap, "DB drop recovery failed.\n");
+}
+static void recover_all_queues(struct adapter *adap)
+{
+ int i;
+
+ for_each_ethrxq(&adap->sge, i)
+ sync_txq_pidx(adap, &adap->sge.ethtxq[i].q);
+ for_each_ofldrxq(&adap->sge, i)
+ sync_txq_pidx(adap, &adap->sge.ofldtxq[i].q);
+ for_each_port(adap, i)
+ sync_txq_pidx(adap, &adap->sge.ctrlq[i].q);
+}
+
+static void notify_rdma_uld(struct adapter *adap, enum cxgb4_control cmd)
+{
+ mutex_lock(&uld_mutex);
+ if (adap->uld_handle[CXGB4_ULD_RDMA])
+ ulds[CXGB4_ULD_RDMA].control(adap->uld_handle[CXGB4_ULD_RDMA],
+ cmd);
+ mutex_unlock(&uld_mutex);
+}
+
+static void process_db_full(struct work_struct *work)
+{
+ struct adapter *adap;
+
+ adap = container_of(work, struct adapter, db_full_task);
+
+ notify_rdma_uld(adap, CXGB4_CONTROL_DB_FULL);
+ drain_db_fifo(adap, dbfifo_drain_delay);
+ t4_set_reg_field(adap, A_SGE_INT_ENABLE3,
+ F_DBFIFO_HP_INT | F_DBFIFO_LP_INT,
+ F_DBFIFO_HP_INT | F_DBFIFO_LP_INT);
+ notify_rdma_uld(adap, CXGB4_CONTROL_DB_EMPTY);
+}
+
+static void process_db_drop(struct work_struct *work)
+{
+ struct adapter *adap;
+
+ adap = container_of(work, struct adapter, db_drop_task);
+
+ t4_set_reg_field(adap, A_SGE_DOORBELL_CONTROL, F_DROPPED_DB, 0);
+ disable_dbs(adap);
+ notify_rdma_uld(adap, CXGB4_CONTROL_DB_DROP);
+ drain_db_fifo(adap, 1);
+ recover_all_queues(adap);
+ enable_dbs(adap);
+}
+
+void t4_db_full(struct adapter *adap)
+{
+ t4_set_reg_field(adap, A_SGE_INT_ENABLE3,
+ F_DBFIFO_HP_INT | F_DBFIFO_LP_INT, 0);
+ queue_work(workq, &adap->db_full_task);
+}
+
+void t4_db_dropped(struct adapter *adap)
+{
+ queue_work(workq, &adap->db_drop_task);
+}
+
static void uld_attach(struct adapter *adap, unsigned int uld)
{
void *handle;
@@ -2479,6 +2682,7 @@ static void uld_attach(struct adapter *adap, unsigned int uld)
lli.gts_reg = adap->regs + MYPF_REG(SGE_PF_GTS);
lli.db_reg = adap->regs + MYPF_REG(SGE_PF_KDOORBELL);
lli.fw_vers = adap->params.fw_vers;
+ lli.dbfifo_int_thresh = dbfifo_int_thresh;
handle = ulds[uld].add(&lli);
if (IS_ERR(handle)) {
@@ -2649,6 +2853,8 @@ static void cxgb_down(struct adapter *adapter)
{
t4_intr_disable(adapter);
cancel_work_sync(&adapter->tid_release_task);
+ cancel_work_sync(&adapter->db_full_task);
+ cancel_work_sync(&adapter->db_drop_task);
adapter->tid_release_task_busy = false;
adapter->tid_release_head = NULL;
@@ -3593,6 +3799,7 @@ static int __devinit init_one(struct pci_dev *pdev,
adapter->pdev = pdev;
adapter->pdev_dev = &pdev->dev;
+ adapter->mbox = func;
adapter->fn = func;
adapter->msg_enable = dflt_msg_enable;
memset(adapter->chan_map, 0xff, sizeof(adapter->chan_map));
@@ -3601,6 +3808,8 @@ static int __devinit init_one(struct pci_dev *pdev,
spin_lock_init(&adapter->tid_release_lock);
INIT_WORK(&adapter->tid_release_task, process_tid_release_list);
+ INIT_WORK(&adapter->db_full_task, process_db_full);
+ INIT_WORK(&adapter->db_drop_task, process_db_drop);
err = t4_prep_adapter(adapter);
if (err)
@@ -3788,6 +3997,10 @@ static int __init cxgb4_init_module(void)
{
int ret;
+ workq = create_singlethread_workqueue("cxgb4");
+ if (!workq)
+ return -ENOMEM;
+
/* Debugfs support is optional, just warn if this fails */
cxgb4_debugfs_root = debugfs_create_dir(KBUILD_MODNAME, NULL);
if (!cxgb4_debugfs_root)
@@ -3803,6 +4016,8 @@ static void __exit cxgb4_cleanup_module(void)
{
pci_unregister_driver(&cxgb4_driver);
debugfs_remove(cxgb4_debugfs_root); /* NULL ok */
+ flush_workqueue(workq);
+ destroy_workqueue(workq);
}
module_init(cxgb4_init_module);
diff --git a/drivers/net/ethernet/chelsio/cxgb4/cxgb4_uld.h b/drivers/net/ethernet/chelsio/cxgb4/cxgb4_uld.h
index b1d39b8d141a..d79980c5fc63 100644
--- a/drivers/net/ethernet/chelsio/cxgb4/cxgb4_uld.h
+++ b/drivers/net/ethernet/chelsio/cxgb4/cxgb4_uld.h
@@ -163,6 +163,12 @@ enum cxgb4_state {
CXGB4_STATE_DETACH
};
+enum cxgb4_control {
+ CXGB4_CONTROL_DB_FULL,
+ CXGB4_CONTROL_DB_EMPTY,
+ CXGB4_CONTROL_DB_DROP,
+};
+
struct pci_dev;
struct l2t_data;
struct net_device;
@@ -212,6 +218,7 @@ struct cxgb4_lld_info {
unsigned short ucq_density; /* # of user CQs/page */
void __iomem *gts_reg; /* address of GTS register */
void __iomem *db_reg; /* address of kernel doorbell */
+ int dbfifo_int_thresh; /* doorbell fifo int threshold */
};
struct cxgb4_uld_info {
@@ -220,11 +227,13 @@ struct cxgb4_uld_info {
int (*rx_handler)(void *handle, const __be64 *rsp,
const struct pkt_gl *gl);
int (*state_change)(void *handle, enum cxgb4_state new_state);
+ int (*control)(void *handle, enum cxgb4_control control, ...);
};
int cxgb4_register_uld(enum cxgb4_uld type, const struct cxgb4_uld_info *p);
int cxgb4_unregister_uld(enum cxgb4_uld type);
int cxgb4_ofld_send(struct net_device *dev, struct sk_buff *skb);
+unsigned int cxgb4_dbfifo_count(const struct net_device *dev, int lpfifo);
unsigned int cxgb4_port_chan(const struct net_device *dev);
unsigned int cxgb4_port_viid(const struct net_device *dev);
unsigned int cxgb4_port_idx(const struct net_device *dev);
@@ -236,4 +245,6 @@ void cxgb4_iscsi_init(struct net_device *dev, unsigned int tag_mask,
const unsigned int *pgsz_order);
struct sk_buff *cxgb4_pktgl_to_skb(const struct pkt_gl *gl,
unsigned int skb_len, unsigned int pull_len);
+int cxgb4_sync_txq_pidx(struct net_device *dev, u16 qid, u16 pidx, u16 size);
+int cxgb4_flush_eq_cache(struct net_device *dev);
#endif /* !__CXGB4_OFLD_H */
diff --git a/drivers/net/ethernet/chelsio/cxgb4/sge.c b/drivers/net/ethernet/chelsio/cxgb4/sge.c
index 2dae7959f000..e111d974afd8 100644
--- a/drivers/net/ethernet/chelsio/cxgb4/sge.c
+++ b/drivers/net/ethernet/chelsio/cxgb4/sge.c
@@ -767,8 +767,13 @@ static void write_sgl(const struct sk_buff *skb, struct sge_txq *q,
static inline void ring_tx_db(struct adapter *adap, struct sge_txq *q, int n)
{
wmb(); /* write descriptors before telling HW */
- t4_write_reg(adap, MYPF_REG(SGE_PF_KDOORBELL),
- QID(q->cntxt_id) | PIDX(n));
+ spin_lock(&q->db_lock);
+ if (!q->db_disabled) {
+ t4_write_reg(adap, MYPF_REG(A_SGE_PF_KDOORBELL),
+ V_QID(q->cntxt_id) | V_PIDX(n));
+ }
+ q->db_pidx = q->pidx;
+ spin_unlock(&q->db_lock);
}
/**
@@ -2081,6 +2086,7 @@ static void init_txq(struct adapter *adap, struct sge_txq *q, unsigned int id)
q->stops = q->restarts = 0;
q->stat = (void *)&q->desc[q->size];
q->cntxt_id = id;
+ spin_lock_init(&q->db_lock);
adap->sge.egr_map[id - adap->sge.egr_start] = q;
}
@@ -2415,6 +2421,18 @@ void t4_sge_init(struct adapter *adap)
RXPKTCPLMODE |
(STAT_LEN == 128 ? EGRSTATUSPAGESIZE : 0));
+ /*
+ * Set up to drop DOORBELL writes when the DOORBELL FIFO overflows
+ * and generate an interrupt when this occurs so we can recover.
+ */
+ t4_set_reg_field(adap, A_SGE_DBFIFO_STATUS,
+ V_HP_INT_THRESH(M_HP_INT_THRESH) |
+ V_LP_INT_THRESH(M_LP_INT_THRESH),
+ V_HP_INT_THRESH(dbfifo_int_thresh) |
+ V_LP_INT_THRESH(dbfifo_int_thresh));
+ t4_set_reg_field(adap, A_SGE_DOORBELL_CONTROL, F_ENABLE_DROP,
+ F_ENABLE_DROP);
+
for (i = v = 0; i < 32; i += 4)
v |= (PAGE_SHIFT - 10) << i;
t4_write_reg(adap, SGE_HOST_PAGE_SIZE, v);
diff --git a/drivers/net/ethernet/chelsio/cxgb4/t4_hw.c b/drivers/net/ethernet/chelsio/cxgb4/t4_hw.c
index d1ec111aebd8..32e1dd566a14 100644
--- a/drivers/net/ethernet/chelsio/cxgb4/t4_hw.c
+++ b/drivers/net/ethernet/chelsio/cxgb4/t4_hw.c
@@ -868,11 +868,14 @@ int t4_restart_aneg(struct adapter *adap, unsigned int mbox, unsigned int port)
return t4_wr_mbox(adap, mbox, &c, sizeof(c), NULL);
}
+typedef void (*int_handler_t)(struct adapter *adap);
+
struct intr_info {
unsigned int mask; /* bits to check in interrupt status */
const char *msg; /* message to print or NULL */
short stat_idx; /* stat counter to increment or -1 */
unsigned short fatal; /* whether the condition reported is fatal */
+ int_handler_t int_handler; /* platform-specific int handler */
};
/**
@@ -905,6 +908,8 @@ static int t4_handle_intr_status(struct adapter *adapter, unsigned int reg,
} else if (acts->msg && printk_ratelimit())
dev_warn(adapter->pdev_dev, "%s (0x%x)\n", acts->msg,
status & acts->mask);
+ if (acts->int_handler)
+ acts->int_handler(adapter);
mask |= acts->mask;
}
status &= mask;
@@ -1013,7 +1018,9 @@ static void sge_intr_handler(struct adapter *adapter)
{ ERR_INVALID_CIDX_INC,
"SGE GTS CIDX increment too large", -1, 0 },
{ ERR_CPL_OPCODE_0, "SGE received 0-length CPL", -1, 0 },
- { ERR_DROPPED_DB, "SGE doorbell dropped", -1, 0 },
+ { F_DBFIFO_LP_INT, NULL, -1, 0, t4_db_full },
+ { F_DBFIFO_HP_INT, NULL, -1, 0, t4_db_full },
+ { F_ERR_DROPPED_DB, NULL, -1, 0, t4_db_dropped },
{ ERR_DATA_CPL_ON_HIGH_QID1 | ERR_DATA_CPL_ON_HIGH_QID0,
"SGE IQID > 1023 received CPL for FL", -1, 0 },
{ ERR_BAD_DB_PIDX3, "SGE DBP 3 pidx increment too large", -1,
@@ -1034,10 +1041,10 @@ static void sge_intr_handler(struct adapter *adapter)
};
v = (u64)t4_read_reg(adapter, SGE_INT_CAUSE1) |
- ((u64)t4_read_reg(adapter, SGE_INT_CAUSE2) << 32);
+ ((u64)t4_read_reg(adapter, SGE_INT_CAUSE2) << 32);
if (v) {
dev_alert(adapter->pdev_dev, "SGE parity error (%#llx)\n",
- (unsigned long long)v);
+ (unsigned long long)v);
t4_write_reg(adapter, SGE_INT_CAUSE1, v);
t4_write_reg(adapter, SGE_INT_CAUSE2, v >> 32);
}
@@ -1513,6 +1520,7 @@ void t4_intr_enable(struct adapter *adapter)
ERR_BAD_DB_PIDX2 | ERR_BAD_DB_PIDX1 |
ERR_BAD_DB_PIDX0 | ERR_ING_CTXT_PRIO |
ERR_EGR_CTXT_PRIO | INGRESS_SIZE_ERR |
+ F_DBFIFO_HP_INT | F_DBFIFO_LP_INT |
EGRESS_SIZE_ERR);
t4_write_reg(adapter, MYPF_REG(PL_PF_INT_ENABLE), PF_INTR_MASK);
t4_set_reg_field(adapter, PL_INT_MAP0, 0, 1 << pf);
@@ -1986,6 +1994,54 @@ int t4_wol_pat_enable(struct adapter *adap, unsigned int port, unsigned int map,
(var).retval_len16 = htonl(FW_LEN16(var)); \
} while (0)
+int t4_fwaddrspace_write(struct adapter *adap, unsigned int mbox,
+ u32 addr, u32 val)
+{
+ struct fw_ldst_cmd c;
+
+ memset(&c, 0, sizeof(c));
+ c.op_to_addrspace = htonl(V_FW_CMD_OP(FW_LDST_CMD) | F_FW_CMD_REQUEST |
+ F_FW_CMD_WRITE |
+ V_FW_LDST_CMD_ADDRSPACE(FW_LDST_ADDRSPC_FIRMWARE));
+ c.cycles_to_len16 = htonl(FW_LEN16(c));
+ c.u.addrval.addr = htonl(addr);
+ c.u.addrval.val = htonl(val);
+
+ return t4_wr_mbox(adap, mbox, &c, sizeof(c), NULL);
+}
+
+/*
+ * t4_mem_win_read_len - read memory through PCIE memory window
+ * @adap: the adapter
+ * @addr: address of first byte requested aligned on 32b.
+ * @data: len bytes to hold the data read
+ * @len: amount of data to read from window. Must be <=
+ * MEMWIN0_APERATURE after adjusting for 16B alignment
+ * requirements of the the memory window.
+ *
+ * Read len bytes of data from MC starting at @addr.
+ */
+int t4_mem_win_read_len(struct adapter *adap, u32 addr, __be32 *data, int len)
+{
+ int i;
+ int off;
+
+ /*
+ * Align on a 16B boundary.
+ */
+ off = addr & 15;
+ if ((addr & 3) || (len + off) > MEMWIN0_APERTURE)
+ return -EINVAL;
+
+ t4_write_reg(adap, A_PCIE_MEM_ACCESS_OFFSET, addr & ~15);
+ t4_read_reg(adap, A_PCIE_MEM_ACCESS_OFFSET);
+
+ for (i = 0; i < len; i += 4)
+ *data++ = t4_read_reg(adap, (MEMWIN0_BASE + off + i));
+
+ return 0;
+}
+
/**
* t4_mdio_rd - read a PHY register through MDIO
* @adap: the adapter
diff --git a/drivers/net/ethernet/chelsio/cxgb4/t4_regs.h b/drivers/net/ethernet/chelsio/cxgb4/t4_regs.h
index 0adc5bcec7c4..111fc323f155 100644
--- a/drivers/net/ethernet/chelsio/cxgb4/t4_regs.h
+++ b/drivers/net/ethernet/chelsio/cxgb4/t4_regs.h
@@ -190,6 +190,59 @@
#define SGE_DEBUG_DATA_LOW 0x10d4
#define SGE_INGRESS_QUEUES_PER_PAGE_PF 0x10f4
+#define S_LP_INT_THRESH 12
+#define V_LP_INT_THRESH(x) ((x) << S_LP_INT_THRESH)
+#define S_HP_INT_THRESH 28
+#define V_HP_INT_THRESH(x) ((x) << S_HP_INT_THRESH)
+#define A_SGE_DBFIFO_STATUS 0x10a4
+
+#define S_ENABLE_DROP 13
+#define V_ENABLE_DROP(x) ((x) << S_ENABLE_DROP)
+#define F_ENABLE_DROP V_ENABLE_DROP(1U)
+#define A_SGE_DOORBELL_CONTROL 0x10a8
+
+#define A_SGE_CTXT_CMD 0x11fc
+#define A_SGE_DBQ_CTXT_BADDR 0x1084
+
+#define A_SGE_PF_KDOORBELL 0x0
+
+#define S_QID 15
+#define V_QID(x) ((x) << S_QID)
+
+#define S_PIDX 0
+#define V_PIDX(x) ((x) << S_PIDX)
+
+#define M_LP_COUNT 0x7ffU
+#define S_LP_COUNT 0
+#define G_LP_COUNT(x) (((x) >> S_LP_COUNT) & M_LP_COUNT)
+
+#define M_HP_COUNT 0x7ffU
+#define S_HP_COUNT 16
+#define G_HP_COUNT(x) (((x) >> S_HP_COUNT) & M_HP_COUNT)
+
+#define A_SGE_INT_ENABLE3 0x1040
+
+#define S_DBFIFO_HP_INT 8
+#define V_DBFIFO_HP_INT(x) ((x) << S_DBFIFO_HP_INT)
+#define F_DBFIFO_HP_INT V_DBFIFO_HP_INT(1U)
+
+#define S_DBFIFO_LP_INT 7
+#define V_DBFIFO_LP_INT(x) ((x) << S_DBFIFO_LP_INT)
+#define F_DBFIFO_LP_INT V_DBFIFO_LP_INT(1U)
+
+#define S_DROPPED_DB 0
+#define V_DROPPED_DB(x) ((x) << S_DROPPED_DB)
+#define F_DROPPED_DB V_DROPPED_DB(1U)
+
+#define S_ERR_DROPPED_DB 18
+#define V_ERR_DROPPED_DB(x) ((x) << S_ERR_DROPPED_DB)
+#define F_ERR_DROPPED_DB V_ERR_DROPPED_DB(1U)
+
+#define A_PCIE_MEM_ACCESS_OFFSET 0x306c
+
+#define M_HP_INT_THRESH 0xfU
+#define M_LP_INT_THRESH 0xfU
+
#define PCIE_PF_CLI 0x44
#define PCIE_INT_CAUSE 0x3004
#define UNXSPLCPLERR 0x20000000U
diff --git a/drivers/net/ethernet/chelsio/cxgb4/t4fw_api.h b/drivers/net/ethernet/chelsio/cxgb4/t4fw_api.h
index edcfd7ec7802..ad53f796b574 100644
--- a/drivers/net/ethernet/chelsio/cxgb4/t4fw_api.h
+++ b/drivers/net/ethernet/chelsio/cxgb4/t4fw_api.h
@@ -1620,4 +1620,19 @@ struct fw_hdr {
#define FW_HDR_FW_VER_MINOR_GET(x) (((x) >> 16) & 0xff)
#define FW_HDR_FW_VER_MICRO_GET(x) (((x) >> 8) & 0xff)
#define FW_HDR_FW_VER_BUILD_GET(x) (((x) >> 0) & 0xff)
+
+#define S_FW_CMD_OP 24
+#define V_FW_CMD_OP(x) ((x) << S_FW_CMD_OP)
+
+#define S_FW_CMD_REQUEST 23
+#define V_FW_CMD_REQUEST(x) ((x) << S_FW_CMD_REQUEST)
+#define F_FW_CMD_REQUEST V_FW_CMD_REQUEST(1U)
+
+#define S_FW_CMD_WRITE 21
+#define V_FW_CMD_WRITE(x) ((x) << S_FW_CMD_WRITE)
+#define F_FW_CMD_WRITE V_FW_CMD_WRITE(1U)
+
+#define S_FW_LDST_CMD_ADDRSPACE 0
+#define V_FW_LDST_CMD_ADDRSPACE(x) ((x) << S_FW_LDST_CMD_ADDRSPACE)
+
#endif /* _T4FW_INTERFACE_H_ */
diff --git a/drivers/net/ethernet/emulex/benet/Makefile b/drivers/net/ethernet/emulex/benet/Makefile
index a60cd8051135..1a91b276940d 100644
--- a/drivers/net/ethernet/emulex/benet/Makefile
+++ b/drivers/net/ethernet/emulex/benet/Makefile
@@ -4,4 +4,4 @@
obj-$(CONFIG_BE2NET) += be2net.o
-be2net-y := be_main.o be_cmds.o be_ethtool.o
+be2net-y := be_main.o be_cmds.o be_ethtool.o be_roce.o
diff --git a/drivers/net/ethernet/emulex/benet/be.h b/drivers/net/ethernet/emulex/benet/be.h
index ff4eb8fe25d5..c5c4c0e83bd1 100644
--- a/drivers/net/ethernet/emulex/benet/be.h
+++ b/drivers/net/ethernet/emulex/benet/be.h
@@ -32,6 +32,7 @@
#include <linux/u64_stats_sync.h>
#include "be_hw.h"
+#include "be_roce.h"
#define DRV_VER "4.2.220u"
#define DRV_NAME "be2net"
@@ -102,7 +103,8 @@ static inline char *nic_name(struct pci_dev *pdev)
#define MAX_RX_QS (MAX_RSS_QS + 1) /* RSS qs + 1 def Rx */
#define MAX_TX_QS 8
-#define MAX_MSIX_VECTORS MAX_RSS_QS
+#define MAX_ROCE_EQS 5
+#define MAX_MSIX_VECTORS (MAX_RSS_QS + MAX_ROCE_EQS) /* RSS qs + RoCE */
#define BE_TX_BUDGET 256
#define BE_NAPI_WEIGHT 64
#define MAX_RX_POST BE_NAPI_WEIGHT /* Frags posted at a time */
@@ -405,6 +407,17 @@ struct be_adapter {
u32 tx_fc; /* Tx flow control */
bool stats_cmd_sent;
u8 generation; /* BladeEngine ASIC generation */
+ u32 if_type;
+ struct {
+ u8 __iomem *base; /* Door Bell */
+ u32 size;
+ u32 total_size;
+ u64 io_addr;
+ } roce_db;
+ u32 num_msix_roce_vec;
+ struct ocrdma_dev *ocrdma_dev;
+ struct list_head entry;
+
u32 flash_status;
struct completion flash_compl;
@@ -441,6 +454,10 @@ struct be_adapter {
#define lancer_chip(adapter) ((adapter->pdev->device == OC_DEVICE_ID3) || \
(adapter->pdev->device == OC_DEVICE_ID4))
+#define be_roce_supported(adapter) ((adapter->if_type == SLI_INTF_TYPE_3 || \
+ adapter->sli_family == SKYHAWK_SLI_FAMILY) && \
+ (adapter->function_mode & RDMA_ENABLED))
+
extern const struct ethtool_ops be_ethtool_ops;
#define msix_enabled(adapter) (adapter->num_msix_vec > 0)
@@ -597,6 +614,12 @@ static inline bool be_is_wol_excluded(struct be_adapter *adapter)
}
}
+static inline bool be_type_2_3(struct be_adapter *adapter)
+{
+ return (adapter->if_type == SLI_INTF_TYPE_2 ||
+ adapter->if_type == SLI_INTF_TYPE_3) ? true : false;
+}
+
extern void be_cq_notify(struct be_adapter *adapter, u16 qid, bool arm,
u16 num_popped);
extern void be_link_status_update(struct be_adapter *adapter, u8 link_status);
@@ -606,4 +629,16 @@ extern bool be_is_wol_supported(struct be_adapter *adapter);
extern bool be_pause_supported(struct be_adapter *adapter);
extern u32 be_get_fw_log_level(struct be_adapter *adapter);
+/*
+ * internal function to initialize-cleanup roce device.
+ */
+extern void be_roce_dev_add(struct be_adapter *);
+extern void be_roce_dev_remove(struct be_adapter *);
+
+/*
+ * internal function to open-close roce device during ifup-ifdown.
+ */
+extern void be_roce_dev_open(struct be_adapter *);
+extern void be_roce_dev_close(struct be_adapter *);
+
#endif /* BE_H */
diff --git a/drivers/net/ethernet/emulex/benet/be_cmds.c b/drivers/net/ethernet/emulex/benet/be_cmds.c
index b24623cce07b..8d06ea381741 100644
--- a/drivers/net/ethernet/emulex/benet/be_cmds.c
+++ b/drivers/net/ethernet/emulex/benet/be_cmds.c
@@ -15,6 +15,7 @@
* Costa Mesa, CA 92626
*/
+#include <linux/module.h>
#include "be.h"
#include "be_cmds.h"
@@ -2646,3 +2647,41 @@ err:
spin_unlock_bh(&adapter->mcc_lock);
return status;
}
+
+int be_roce_mcc_cmd(void *netdev_handle, void *wrb_payload,
+ int wrb_payload_size, u16 *cmd_status, u16 *ext_status)
+{
+ struct be_adapter *adapter = netdev_priv(netdev_handle);
+ struct be_mcc_wrb *wrb;
+ struct be_cmd_req_hdr *hdr = (struct be_cmd_req_hdr *) wrb_payload;
+ struct be_cmd_req_hdr *req;
+ struct be_cmd_resp_hdr *resp;
+ int status;
+
+ spin_lock_bh(&adapter->mcc_lock);
+
+ wrb = wrb_from_mccq(adapter);
+ if (!wrb) {
+ status = -EBUSY;
+ goto err;
+ }
+ req = embedded_payload(wrb);
+ resp = embedded_payload(wrb);
+
+ be_wrb_cmd_hdr_prepare(req, hdr->subsystem,
+ hdr->opcode, wrb_payload_size, wrb, NULL);
+ memcpy(req, wrb_payload, wrb_payload_size);
+ be_dws_cpu_to_le(req, wrb_payload_size);
+
+ status = be_mcc_notify_wait(adapter);
+ if (cmd_status)
+ *cmd_status = (status & 0xffff);
+ if (ext_status)
+ *ext_status = 0;
+ memcpy(wrb_payload, resp, sizeof(*resp) + resp->response_length);
+ be_dws_le_to_cpu(wrb_payload, sizeof(*resp) + resp->response_length);
+err:
+ spin_unlock_bh(&adapter->mcc_lock);
+ return status;
+}
+EXPORT_SYMBOL(be_roce_mcc_cmd);
diff --git a/drivers/net/ethernet/emulex/benet/be_cmds.h b/drivers/net/ethernet/emulex/benet/be_cmds.h
index 0b1029b60f69..9625bf420c16 100644
--- a/drivers/net/ethernet/emulex/benet/be_cmds.h
+++ b/drivers/net/ethernet/emulex/benet/be_cmds.h
@@ -1062,6 +1062,7 @@ struct be_cmd_resp_modify_eq_delay {
/* The HW can come up in either of the following multi-channel modes
* based on the skew/IPL.
*/
+#define RDMA_ENABLED 0x4
#define FLEX10_MODE 0x400
#define VNIC_MODE 0x20000
#define UMC_ENABLED 0x1000000
diff --git a/drivers/net/ethernet/emulex/benet/be_hw.h b/drivers/net/ethernet/emulex/benet/be_hw.h
index f38b58c8dbba..d9fb0c501fa1 100644
--- a/drivers/net/ethernet/emulex/benet/be_hw.h
+++ b/drivers/net/ethernet/emulex/benet/be_hw.h
@@ -100,11 +100,13 @@
#define SLI_INTF_REV_SHIFT 4
#define SLI_INTF_FT_MASK 0x00000001
+#define SLI_INTF_TYPE_2 2
+#define SLI_INTF_TYPE_3 3
/* SLI family */
#define BE_SLI_FAMILY 0x0
#define LANCER_A0_SLI_FAMILY 0xA
-
+#define SKYHAWK_SLI_FAMILY 0x2
/********* ISR0 Register offset **********/
#define CEV_ISR0_OFFSET 0xC18
diff --git a/drivers/net/ethernet/emulex/benet/be_main.c b/drivers/net/ethernet/emulex/benet/be_main.c
index 081c77701168..08efd308d78a 100644
--- a/drivers/net/ethernet/emulex/benet/be_main.c
+++ b/drivers/net/ethernet/emulex/benet/be_main.c
@@ -2151,10 +2151,17 @@ static uint be_num_rss_want(struct be_adapter *adapter)
static void be_msix_enable(struct be_adapter *adapter)
{
#define BE_MIN_MSIX_VECTORS 1
- int i, status, num_vec;
+ int i, status, num_vec, num_roce_vec = 0;
/* If RSS queues are not used, need a vec for default RX Q */
num_vec = min(be_num_rss_want(adapter), num_online_cpus());
+ if (be_roce_supported(adapter)) {
+ num_roce_vec = min_t(u32, MAX_ROCE_MSIX_VECTORS,
+ (num_online_cpus() + 1));
+ num_roce_vec = min(num_roce_vec, MAX_ROCE_EQS);
+ num_vec += num_roce_vec;
+ num_vec = min(num_vec, MAX_MSIX_VECTORS);
+ }
num_vec = max(num_vec, BE_MIN_MSIX_VECTORS);
for (i = 0; i < num_vec; i++)
@@ -2171,7 +2178,17 @@ static void be_msix_enable(struct be_adapter *adapter)
}
return;
done:
- adapter->num_msix_vec = num_vec;
+ if (be_roce_supported(adapter)) {
+ if (num_vec > num_roce_vec) {
+ adapter->num_msix_vec = num_vec - num_roce_vec;
+ adapter->num_msix_roce_vec =
+ num_vec - adapter->num_msix_vec;
+ } else {
+ adapter->num_msix_vec = num_vec;
+ adapter->num_msix_roce_vec = 0;
+ }
+ } else
+ adapter->num_msix_vec = num_vec;
return;
}
@@ -2283,6 +2300,8 @@ static int be_close(struct net_device *netdev)
struct be_eq_obj *eqo;
int i;
+ be_roce_dev_close(adapter);
+
be_async_mcc_disable(adapter);
if (!lancer_chip(adapter))
@@ -2391,6 +2410,7 @@ static int be_open(struct net_device *netdev)
if (!status)
be_link_status_update(adapter, link_status);
+ be_roce_dev_open(adapter);
return 0;
err:
be_close(adapter->netdev);
@@ -3232,6 +3252,24 @@ static void be_unmap_pci_bars(struct be_adapter *adapter)
iounmap(adapter->csr);
if (adapter->db)
iounmap(adapter->db);
+ if (adapter->roce_db.base)
+ pci_iounmap(adapter->pdev, adapter->roce_db.base);
+}
+
+static int lancer_roce_map_pci_bars(struct be_adapter *adapter)
+{
+ struct pci_dev *pdev = adapter->pdev;
+ u8 __iomem *addr;
+
+ addr = pci_iomap(pdev, 2, 0);
+ if (addr == NULL)
+ return -ENOMEM;
+
+ adapter->roce_db.base = addr;
+ adapter->roce_db.io_addr = pci_resource_start(pdev, 2);
+ adapter->roce_db.size = 8192;
+ adapter->roce_db.total_size = pci_resource_len(pdev, 2);
+ return 0;
}
static int be_map_pci_bars(struct be_adapter *adapter)
@@ -3240,11 +3278,18 @@ static int be_map_pci_bars(struct be_adapter *adapter)
int db_reg;
if (lancer_chip(adapter)) {
- addr = ioremap_nocache(pci_resource_start(adapter->pdev, 0),
- pci_resource_len(adapter->pdev, 0));
- if (addr == NULL)
- return -ENOMEM;
- adapter->db = addr;
+ if (be_type_2_3(adapter)) {
+ addr = ioremap_nocache(
+ pci_resource_start(adapter->pdev, 0),
+ pci_resource_len(adapter->pdev, 0));
+ if (addr == NULL)
+ return -ENOMEM;
+ adapter->db = addr;
+ }
+ if (adapter->if_type == SLI_INTF_TYPE_3) {
+ if (lancer_roce_map_pci_bars(adapter))
+ goto pci_map_err;
+ }
return 0;
}
@@ -3269,14 +3314,19 @@ static int be_map_pci_bars(struct be_adapter *adapter)
if (addr == NULL)
goto pci_map_err;
adapter->db = addr;
-
+ if (adapter->sli_family == SKYHAWK_SLI_FAMILY) {
+ adapter->roce_db.size = 4096;
+ adapter->roce_db.io_addr =
+ pci_resource_start(adapter->pdev, db_reg);
+ adapter->roce_db.total_size =
+ pci_resource_len(adapter->pdev, db_reg);
+ }
return 0;
pci_map_err:
be_unmap_pci_bars(adapter);
return -ENOMEM;
}
-
static void be_ctrl_cleanup(struct be_adapter *adapter)
{
struct be_dma_mem *mem = &adapter->mbox_mem_alloced;
@@ -3382,6 +3432,8 @@ static void __devexit be_remove(struct pci_dev *pdev)
if (!adapter)
return;
+ be_roce_dev_remove(adapter);
+
unregister_netdev(adapter->netdev);
be_clear(adapter);
@@ -3495,17 +3547,27 @@ static int be_dev_type_check(struct be_adapter *adapter)
break;
case BE_DEVICE_ID2:
case OC_DEVICE_ID2:
- case OC_DEVICE_ID5:
adapter->generation = BE_GEN3;
break;
case OC_DEVICE_ID3:
case OC_DEVICE_ID4:
pci_read_config_dword(pdev, SLI_INTF_REG_OFFSET, &sli_intf);
+ adapter->if_type = (sli_intf & SLI_INTF_IF_TYPE_MASK) >>
+ SLI_INTF_IF_TYPE_SHIFT;
if_type = (sli_intf & SLI_INTF_IF_TYPE_MASK) >>
SLI_INTF_IF_TYPE_SHIFT;
-
if (((sli_intf & SLI_INTF_VALID_MASK) != SLI_INTF_VALID) ||
- if_type != 0x02) {
+ !be_type_2_3(adapter)) {
+ dev_err(&pdev->dev, "SLI_INTF reg val is not valid\n");
+ return -EINVAL;
+ }
+ adapter->sli_family = ((sli_intf & SLI_INTF_FAMILY_MASK) >>
+ SLI_INTF_FAMILY_SHIFT);
+ adapter->generation = BE_GEN3;
+ break;
+ case OC_DEVICE_ID5:
+ pci_read_config_dword(pdev, SLI_INTF_REG_OFFSET, &sli_intf);
+ if ((sli_intf & SLI_INTF_VALID_MASK) != SLI_INTF_VALID) {
dev_err(&pdev->dev, "SLI_INTF reg val is not valid\n");
return -EINVAL;
}
@@ -3774,6 +3836,8 @@ static int __devinit be_probe(struct pci_dev *pdev,
if (status != 0)
goto unsetup;
+ be_roce_dev_add(adapter);
+
dev_info(&pdev->dev, "%s: %s port %d\n", netdev->name, nic_name(pdev),
adapter->port_num);
diff --git a/drivers/net/ethernet/emulex/benet/be_roce.c b/drivers/net/ethernet/emulex/benet/be_roce.c
new file mode 100644
index 000000000000..deecc44b3617
--- /dev/null
+++ b/drivers/net/ethernet/emulex/benet/be_roce.c
@@ -0,0 +1,182 @@
+/*
+ * Copyright (C) 2005 - 2011 Emulex
+ * All rights reserved.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License version 2
+ * as published by the Free Software Foundation. The full GNU General
+ * Public License is included in this distribution in the file called COPYING.
+ *
+ * Contact Information:
+ * linux-drivers@emulex.com
+ *
+ * Emulex
+ * 3333 Susan Street
+ * Costa Mesa, CA 92626
+ */
+
+#include <linux/mutex.h>
+#include <linux/list.h>
+#include <linux/netdevice.h>
+#include <linux/module.h>
+
+#include "be.h"
+#include "be_cmds.h"
+
+static struct ocrdma_driver *ocrdma_drv;
+static LIST_HEAD(be_adapter_list);
+static DEFINE_MUTEX(be_adapter_list_lock);
+
+static void _be_roce_dev_add(struct be_adapter *adapter)
+{
+ struct be_dev_info dev_info;
+ int i, num_vec;
+ struct pci_dev *pdev = adapter->pdev;
+
+ if (!ocrdma_drv)
+ return;
+ if (pdev->device == OC_DEVICE_ID5) {
+ /* only msix is supported on these devices */
+ if (!msix_enabled(adapter))
+ return;
+ /* DPP region address and length */
+ dev_info.dpp_unmapped_addr = pci_resource_start(pdev, 2);
+ dev_info.dpp_unmapped_len = pci_resource_len(pdev, 2);
+ } else {
+ dev_info.dpp_unmapped_addr = 0;
+ dev_info.dpp_unmapped_len = 0;
+ }
+ dev_info.pdev = adapter->pdev;
+ if (adapter->sli_family == SKYHAWK_SLI_FAMILY)
+ dev_info.db = adapter->db;
+ else
+ dev_info.db = adapter->roce_db.base;
+ dev_info.unmapped_db = adapter->roce_db.io_addr;
+ dev_info.db_page_size = adapter->roce_db.size;
+ dev_info.db_total_size = adapter->roce_db.total_size;
+ dev_info.netdev = adapter->netdev;
+ memcpy(dev_info.mac_addr, adapter->netdev->dev_addr, ETH_ALEN);
+ dev_info.dev_family = adapter->sli_family;
+ if (msix_enabled(adapter)) {
+ /* provide all the vectors, so that EQ creation response
+ * can decide which one to use.
+ */
+ num_vec = adapter->num_msix_vec + adapter->num_msix_roce_vec;
+ dev_info.intr_mode = BE_INTERRUPT_MODE_MSIX;
+ dev_info.msix.num_vectors = min(num_vec, MAX_ROCE_MSIX_VECTORS);
+ /* provide start index of the vector,
+ * so in case of linear usage,
+ * it can use the base as starting point.
+ */
+ dev_info.msix.start_vector = adapter->num_evt_qs;
+ for (i = 0; i < dev_info.msix.num_vectors; i++) {
+ dev_info.msix.vector_list[i] =
+ adapter->msix_entries[i].vector;
+ }
+ } else {
+ dev_info.msix.num_vectors = 0;
+ dev_info.intr_mode = BE_INTERRUPT_MODE_INTX;
+ }
+ adapter->ocrdma_dev = ocrdma_drv->add(&dev_info);
+}
+
+void be_roce_dev_add(struct be_adapter *adapter)
+{
+ if (be_roce_supported(adapter)) {
+ INIT_LIST_HEAD(&adapter->entry);
+ mutex_lock(&be_adapter_list_lock);
+ list_add_tail(&adapter->entry, &be_adapter_list);
+
+ /* invoke add() routine of roce driver only if
+ * valid driver registered with add method and add() is not yet
+ * invoked on a given adapter.
+ */
+ _be_roce_dev_add(adapter);
+ mutex_unlock(&be_adapter_list_lock);
+ }
+}
+
+void _be_roce_dev_remove(struct be_adapter *adapter)
+{
+ if (ocrdma_drv && ocrdma_drv->remove && adapter->ocrdma_dev)
+ ocrdma_drv->remove(adapter->ocrdma_dev);
+ adapter->ocrdma_dev = NULL;
+}
+
+void be_roce_dev_remove(struct be_adapter *adapter)
+{
+ if (be_roce_supported(adapter)) {
+ mutex_lock(&be_adapter_list_lock);
+ _be_roce_dev_remove(adapter);
+ list_del(&adapter->entry);
+ mutex_unlock(&be_adapter_list_lock);
+ }
+}
+
+void _be_roce_dev_open(struct be_adapter *adapter)
+{
+ if (ocrdma_drv && adapter->ocrdma_dev &&
+ ocrdma_drv->state_change_handler)
+ ocrdma_drv->state_change_handler(adapter->ocrdma_dev, 0);
+}
+
+void be_roce_dev_open(struct be_adapter *adapter)
+{
+ if (be_roce_supported(adapter)) {
+ mutex_lock(&be_adapter_list_lock);
+ _be_roce_dev_open(adapter);
+ mutex_unlock(&be_adapter_list_lock);
+ }
+}
+
+void _be_roce_dev_close(struct be_adapter *adapter)
+{
+ if (ocrdma_drv && adapter->ocrdma_dev &&
+ ocrdma_drv->state_change_handler)
+ ocrdma_drv->state_change_handler(adapter->ocrdma_dev, 1);
+}
+
+void be_roce_dev_close(struct be_adapter *adapter)
+{
+ if (be_roce_supported(adapter)) {
+ mutex_lock(&be_adapter_list_lock);
+ _be_roce_dev_close(adapter);
+ mutex_unlock(&be_adapter_list_lock);
+ }
+}
+
+int be_roce_register_driver(struct ocrdma_driver *drv)
+{
+ struct be_adapter *dev;
+
+ mutex_lock(&be_adapter_list_lock);
+ if (ocrdma_drv) {
+ mutex_unlock(&be_adapter_list_lock);
+ return -EINVAL;
+ }
+ ocrdma_drv = drv;
+ list_for_each_entry(dev, &be_adapter_list, entry) {
+ struct net_device *netdev;
+ _be_roce_dev_add(dev);
+ netdev = dev->netdev;
+ if (netif_running(netdev) && netif_oper_up(netdev))
+ _be_roce_dev_open(dev);
+ }
+ mutex_unlock(&be_adapter_list_lock);
+ return 0;
+}
+EXPORT_SYMBOL(be_roce_register_driver);
+
+void be_roce_unregister_driver(struct ocrdma_driver *drv)
+{
+ struct be_adapter *dev;
+
+ mutex_lock(&be_adapter_list_lock);
+ list_for_each_entry(dev, &be_adapter_list, entry) {
+ if (dev->ocrdma_dev)
+ _be_roce_dev_remove(dev);
+ }
+ ocrdma_drv = NULL;
+ mutex_unlock(&be_adapter_list_lock);
+}
+EXPORT_SYMBOL(be_roce_unregister_driver);
diff --git a/drivers/net/ethernet/emulex/benet/be_roce.h b/drivers/net/ethernet/emulex/benet/be_roce.h
new file mode 100644
index 000000000000..db4ea8081c07
--- /dev/null
+++ b/drivers/net/ethernet/emulex/benet/be_roce.h
@@ -0,0 +1,75 @@
+/*
+ * Copyright (C) 2005 - 2011 Emulex
+ * All rights reserved.
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU General Public License version 2
+ * as published by the Free Software Foundation. The full GNU General
+ * Public License is included in this distribution in the file called COPYING.
+ *
+ * Contact Information:
+ * linux-drivers@emulex.com
+ *
+ * Emulex
+ * 3333 Susan Street
+ * Costa Mesa, CA 92626
+ */
+
+#ifndef BE_ROCE_H
+#define BE_ROCE_H
+
+#include <linux/pci.h>
+#include <linux/netdevice.h>
+
+struct ocrdma_dev;
+
+enum be_interrupt_mode {
+ BE_INTERRUPT_MODE_MSIX = 0,
+ BE_INTERRUPT_MODE_INTX = 1,
+ BE_INTERRUPT_MODE_MSI = 2,
+};
+
+#define MAX_ROCE_MSIX_VECTORS 16
+struct be_dev_info {
+ u8 __iomem *db;
+ u64 unmapped_db;
+ u32 db_page_size;
+ u32 db_total_size;
+ u64 dpp_unmapped_addr;
+ u32 dpp_unmapped_len;
+ struct pci_dev *pdev;
+ struct net_device *netdev;
+ u8 mac_addr[ETH_ALEN];
+ u32 dev_family;
+ enum be_interrupt_mode intr_mode;
+ struct {
+ int num_vectors;
+ int start_vector;
+ u32 vector_list[MAX_ROCE_MSIX_VECTORS];
+ } msix;
+};
+
+/* ocrdma driver register's the callback functions with nic driver. */
+struct ocrdma_driver {
+ unsigned char name[32];
+ struct ocrdma_dev *(*add) (struct be_dev_info *dev_info);
+ void (*remove) (struct ocrdma_dev *);
+ void (*state_change_handler) (struct ocrdma_dev *, u32 new_state);
+};
+
+enum {
+ BE_DEV_UP = 0,
+ BE_DEV_DOWN = 1
+};
+
+/* APIs for RoCE driver to register callback handlers,
+ * which will be invoked when device is added, removed, ifup, ifdown
+ */
+int be_roce_register_driver(struct ocrdma_driver *drv);
+void be_roce_unregister_driver(struct ocrdma_driver *drv);
+
+/* API for RoCE driver to issue mailbox commands */
+int be_roce_mcc_cmd(void *netdev_handle, void *wrb_payload,
+ int wrb_payload_size, u16 *cmd_status, u16 *ext_status);
+
+#endif /* BE_ROCE_H */
diff --git a/drivers/net/ethernet/freescale/fec.c b/drivers/net/ethernet/freescale/fec.c
index 7fa0227c9c02..8f2cf8c09e2d 100644
--- a/drivers/net/ethernet/freescale/fec.c
+++ b/drivers/net/ethernet/freescale/fec.c
@@ -48,6 +48,7 @@
#include <linux/of_device.h>
#include <linux/of_gpio.h>
#include <linux/of_net.h>
+#include <linux/pinctrl/consumer.h>
#include <asm/cacheflush.h>
@@ -1543,6 +1544,7 @@ fec_probe(struct platform_device *pdev)
struct resource *r;
const struct of_device_id *of_id;
static int dev_id;
+ struct pinctrl *pinctrl;
of_id = of_match_device(fec_dt_ids, &pdev->dev);
if (of_id)
@@ -1610,6 +1612,12 @@ fec_probe(struct platform_device *pdev)
}
}
+ pinctrl = devm_pinctrl_get_select_default(&pdev->dev);
+ if (IS_ERR(pinctrl)) {
+ ret = PTR_ERR(pinctrl);
+ goto failed_pin;
+ }
+
fep->clk = clk_get(&pdev->dev, NULL);
if (IS_ERR(fep->clk)) {
ret = PTR_ERR(fep->clk);
@@ -1640,6 +1648,7 @@ failed_mii_init:
failed_init:
clk_disable_unprepare(fep->clk);
clk_put(fep->clk);
+failed_pin:
failed_clk:
for (i = 0; i < FEC_IRQ_NUM; i++) {
irq = platform_get_irq(pdev, i);
diff --git a/drivers/net/ethernet/mellanox/mlx4/alloc.c b/drivers/net/ethernet/mellanox/mlx4/alloc.c
index 8be20e7ea3d1..06fef5b44f77 100644
--- a/drivers/net/ethernet/mellanox/mlx4/alloc.c
+++ b/drivers/net/ethernet/mellanox/mlx4/alloc.c
@@ -124,9 +124,6 @@ void mlx4_bitmap_free_range(struct mlx4_bitmap *bitmap, u32 obj, int cnt)
spin_lock(&bitmap->lock);
bitmap_clear(bitmap->table, obj, cnt);
- bitmap->last = min(bitmap->last, obj);
- bitmap->top = (bitmap->top + bitmap->max + bitmap->reserved_top)
- & bitmap->mask;
bitmap->avail += cnt;
spin_unlock(&bitmap->lock);
}
diff --git a/drivers/net/ethernet/mellanox/mlx4/fw.c b/drivers/net/ethernet/mellanox/mlx4/fw.c
index 24429a99190d..68f5cd6cb3c7 100644
--- a/drivers/net/ethernet/mellanox/mlx4/fw.c
+++ b/drivers/net/ethernet/mellanox/mlx4/fw.c
@@ -118,6 +118,20 @@ static void dump_dev_cap_flags(struct mlx4_dev *dev, u64 flags)
mlx4_dbg(dev, " %s\n", fname[i]);
}
+static void dump_dev_cap_flags2(struct mlx4_dev *dev, u64 flags)
+{
+ static const char * const fname[] = {
+ [0] = "RSS support",
+ [1] = "RSS Toeplitz Hash Function support",
+ [2] = "RSS XOR Hash Function support"
+ };
+ int i;
+
+ for (i = 0; i < ARRAY_SIZE(fname); ++i)
+ if (fname[i] && (flags & (1LL << i)))
+ mlx4_dbg(dev, " %s\n", fname[i]);
+}
+
int mlx4_MOD_STAT_CFG(struct mlx4_dev *dev, struct mlx4_mod_stat_cfg *cfg)
{
struct mlx4_cmd_mailbox *mailbox;
@@ -346,6 +360,7 @@ int mlx4_QUERY_DEV_CAP(struct mlx4_dev *dev, struct mlx4_dev_cap *dev_cap)
#define QUERY_DEV_CAP_MAX_REQ_QP_OFFSET 0x29
#define QUERY_DEV_CAP_MAX_RES_QP_OFFSET 0x2b
#define QUERY_DEV_CAP_MAX_GSO_OFFSET 0x2d
+#define QUERY_DEV_CAP_RSS_OFFSET 0x2e
#define QUERY_DEV_CAP_MAX_RDMA_OFFSET 0x2f
#define QUERY_DEV_CAP_RSZ_SRQ_OFFSET 0x33
#define QUERY_DEV_CAP_ACK_DELAY_OFFSET 0x35
@@ -390,6 +405,7 @@ int mlx4_QUERY_DEV_CAP(struct mlx4_dev *dev, struct mlx4_dev_cap *dev_cap)
#define QUERY_DEV_CAP_RSVD_LKEY_OFFSET 0x98
#define QUERY_DEV_CAP_MAX_ICM_SZ_OFFSET 0xa0
+ dev_cap->flags2 = 0;
mailbox = mlx4_alloc_cmd_mailbox(dev);
if (IS_ERR(mailbox))
return PTR_ERR(mailbox);
@@ -439,6 +455,17 @@ int mlx4_QUERY_DEV_CAP(struct mlx4_dev *dev, struct mlx4_dev_cap *dev_cap)
else
dev_cap->max_gso_sz = 1 << field;
+ MLX4_GET(field, outbox, QUERY_DEV_CAP_RSS_OFFSET);
+ if (field & 0x20)
+ dev_cap->flags2 |= MLX4_DEV_CAP_FLAG2_RSS_XOR;
+ if (field & 0x10)
+ dev_cap->flags2 |= MLX4_DEV_CAP_FLAG2_RSS_TOP;
+ field &= 0xf;
+ if (field) {
+ dev_cap->flags2 |= MLX4_DEV_CAP_FLAG2_RSS;
+ dev_cap->max_rss_tbl_sz = 1 << field;
+ } else
+ dev_cap->max_rss_tbl_sz = 0;
MLX4_GET(field, outbox, QUERY_DEV_CAP_MAX_RDMA_OFFSET);
dev_cap->max_rdma_global = 1 << (field & 0x3f);
MLX4_GET(field, outbox, QUERY_DEV_CAP_ACK_DELAY_OFFSET);
@@ -632,8 +659,10 @@ int mlx4_QUERY_DEV_CAP(struct mlx4_dev *dev, struct mlx4_dev_cap *dev_cap)
dev_cap->max_rq_desc_sz, dev_cap->max_rq_sg);
mlx4_dbg(dev, "Max GSO size: %d\n", dev_cap->max_gso_sz);
mlx4_dbg(dev, "Max counters: %d\n", dev_cap->max_counters);
+ mlx4_dbg(dev, "Max RSS Table size: %d\n", dev_cap->max_rss_tbl_sz);
dump_dev_cap_flags(dev, dev_cap->flags);
+ dump_dev_cap_flags2(dev, dev_cap->flags2);
out:
mlx4_free_cmd_mailbox(dev, mailbox);
diff --git a/drivers/net/ethernet/mellanox/mlx4/fw.h b/drivers/net/ethernet/mellanox/mlx4/fw.h
index e1a5fa56bcbc..64c0399e4b78 100644
--- a/drivers/net/ethernet/mellanox/mlx4/fw.h
+++ b/drivers/net/ethernet/mellanox/mlx4/fw.h
@@ -79,6 +79,7 @@ struct mlx4_dev_cap {
u64 trans_code[MLX4_MAX_PORTS + 1];
u16 stat_rate_support;
u64 flags;
+ u64 flags2;
int reserved_uars;
int uar_size;
int min_page_sz;
@@ -110,6 +111,7 @@ struct mlx4_dev_cap {
u32 reserved_lkey;
u64 max_icm_sz;
int max_gso_sz;
+ int max_rss_tbl_sz;
u8 supported_port_types[MLX4_MAX_PORTS + 1];
u8 suggested_type[MLX4_MAX_PORTS + 1];
u8 default_sense[MLX4_MAX_PORTS + 1];
diff --git a/drivers/net/ethernet/mellanox/mlx4/main.c b/drivers/net/ethernet/mellanox/mlx4/main.c
index 984ace44104f..2e024a68fa81 100644
--- a/drivers/net/ethernet/mellanox/mlx4/main.c
+++ b/drivers/net/ethernet/mellanox/mlx4/main.c
@@ -272,10 +272,12 @@ static int mlx4_dev_cap(struct mlx4_dev *dev, struct mlx4_dev_cap *dev_cap)
dev->caps.max_msg_sz = dev_cap->max_msg_sz;
dev->caps.page_size_cap = ~(u32) (dev_cap->min_page_sz - 1);
dev->caps.flags = dev_cap->flags;
+ dev->caps.flags2 = dev_cap->flags2;
dev->caps.bmme_flags = dev_cap->bmme_flags;
dev->caps.reserved_lkey = dev_cap->reserved_lkey;
dev->caps.stat_rate_support = dev_cap->stat_rate_support;
dev->caps.max_gso_sz = dev_cap->max_gso_sz;
+ dev->caps.max_rss_tbl_sz = dev_cap->max_rss_tbl_sz;
/* Sense port always allowed on supported devices for ConnectX1 and 2 */
if (dev->pdev->device != 0x1003)
diff --git a/drivers/net/ethernet/nxp/lpc_eth.c b/drivers/net/ethernet/nxp/lpc_eth.c
index d3469d8e3f0d..8d2666fcffd7 100644
--- a/drivers/net/ethernet/nxp/lpc_eth.c
+++ b/drivers/net/ethernet/nxp/lpc_eth.c
@@ -40,6 +40,7 @@
#include <linux/skbuff.h>
#include <linux/phy.h>
#include <linux/dma-mapping.h>
+#include <linux/of.h>
#include <linux/of_net.h>
#include <linux/types.h>
@@ -340,13 +341,17 @@
*/
#define LPC_POWERDOWN_MACAHB (1 << 31)
-/* Upon the upcoming introduction of device tree usage in LPC32xx,
- * lpc_phy_interface_mode() and use_iram_for_net() will be extended with a
- * device parameter for access to device tree information at runtime, instead
- * of defining the values at compile time
- */
-static inline phy_interface_t lpc_phy_interface_mode(void)
+static phy_interface_t lpc_phy_interface_mode(struct device *dev)
{
+ if (dev && dev->of_node) {
+ const char *mode = of_get_property(dev->of_node,
+ "phy-mode", NULL);
+ if (mode && !strcmp(mode, "mii"))
+ return PHY_INTERFACE_MODE_MII;
+ return PHY_INTERFACE_MODE_RMII;
+ }
+
+ /* non-DT */
#ifdef CONFIG_ARCH_LPC32XX_MII_SUPPORT
return PHY_INTERFACE_MODE_MII;
#else
@@ -354,12 +359,16 @@ static inline phy_interface_t lpc_phy_interface_mode(void)
#endif
}
-static inline int use_iram_for_net(void)
+static bool use_iram_for_net(struct device *dev)
{
+ if (dev && dev->of_node)
+ return of_property_read_bool(dev->of_node, "use-iram");
+
+ /* non-DT */
#ifdef CONFIG_ARCH_LPC32XX_IRAM_FOR_NET
- return 1;
+ return true;
#else
- return 0;
+ return false;
#endif
}
@@ -664,7 +673,7 @@ static void __lpc_eth_init(struct netdata_local *pldat)
LPC_ENET_CLRT(pldat->net_base));
writel(LPC_IPGR_LOAD_PART2(0x12), LPC_ENET_IPGR(pldat->net_base));
- if (lpc_phy_interface_mode() == PHY_INTERFACE_MODE_MII)
+ if (lpc_phy_interface_mode(&pldat->pdev->dev) == PHY_INTERFACE_MODE_MII)
writel(LPC_COMMAND_PASSRUNTFRAME,
LPC_ENET_COMMAND(pldat->net_base));
else {
@@ -804,12 +813,13 @@ static int lpc_mii_probe(struct net_device *ndev)
}
/* Attach to the PHY */
- if (lpc_phy_interface_mode() == PHY_INTERFACE_MODE_MII)
+ if (lpc_phy_interface_mode(&pldat->pdev->dev) == PHY_INTERFACE_MODE_MII)
netdev_info(ndev, "using MII interface\n");
else
netdev_info(ndev, "using RMII interface\n");
phydev = phy_connect(ndev, dev_name(&phydev->dev),
- &lpc_handle_link_change, 0, lpc_phy_interface_mode());
+ &lpc_handle_link_change, 0,
+ lpc_phy_interface_mode(&pldat->pdev->dev));
if (IS_ERR(phydev)) {
netdev_err(ndev, "Could not attach to PHY\n");
@@ -843,7 +853,7 @@ static int lpc_mii_init(struct netdata_local *pldat)
}
/* Setup MII mode */
- if (lpc_phy_interface_mode() == PHY_INTERFACE_MODE_MII)
+ if (lpc_phy_interface_mode(&pldat->pdev->dev) == PHY_INTERFACE_MODE_MII)
writel(LPC_COMMAND_PASSRUNTFRAME,
LPC_ENET_COMMAND(pldat->net_base));
else {
@@ -1315,18 +1325,26 @@ static const struct net_device_ops lpc_netdev_ops = {
static int lpc_eth_drv_probe(struct platform_device *pdev)
{
struct resource *res;
- struct resource *dma_res;
struct net_device *ndev;
struct netdata_local *pldat;
struct phy_device *phydev;
dma_addr_t dma_handle;
int irq, ret;
+ u32 tmp;
+
+ /* Setup network interface for RMII or MII mode */
+ tmp = __raw_readl(LPC32XX_CLKPWR_MACCLK_CTRL);
+ tmp &= ~LPC32XX_CLKPWR_MACCTRL_PINS_MSK;
+ if (lpc_phy_interface_mode(&pdev->dev) == PHY_INTERFACE_MODE_MII)
+ tmp |= LPC32XX_CLKPWR_MACCTRL_USE_MII_PINS;
+ else
+ tmp |= LPC32XX_CLKPWR_MACCTRL_USE_RMII_PINS;
+ __raw_writel(tmp, LPC32XX_CLKPWR_MACCLK_CTRL);
/* Get platform resources */
res = platform_get_resource(pdev, IORESOURCE_MEM, 0);
- dma_res = platform_get_resource(pdev, IORESOURCE_MEM, 1);
irq = platform_get_irq(pdev, 0);
- if ((!res) || (!dma_res) || (irq < 0) || (irq >= NR_IRQS)) {
+ if ((!res) || (irq < 0) || (irq >= NR_IRQS)) {
dev_err(&pdev->dev, "error getting resources.\n");
ret = -ENXIO;
goto err_exit;
@@ -1389,17 +1407,19 @@ static int lpc_eth_drv_probe(struct platform_device *pdev)
sizeof(struct txrx_desc_t) + sizeof(struct rx_status_t));
pldat->dma_buff_base_v = 0;
- if (use_iram_for_net()) {
- dma_handle = dma_res->start;
+ if (use_iram_for_net(&pldat->pdev->dev)) {
+ dma_handle = LPC32XX_IRAM_BASE;
if (pldat->dma_buff_size <= lpc32xx_return_iram_size())
pldat->dma_buff_base_v =
- io_p2v(dma_res->start);
+ io_p2v(LPC32XX_IRAM_BASE);
else
netdev_err(ndev,
"IRAM not big enough for net buffers, using SDRAM instead.\n");
}
if (pldat->dma_buff_base_v == 0) {
+ pldat->pdev->dev.coherent_dma_mask = 0xFFFFFFFF;
+ pldat->pdev->dev.dma_mask = &pldat->pdev->dev.coherent_dma_mask;
pldat->dma_buff_size = PAGE_ALIGN(pldat->dma_buff_size);
/* Allocate a chunk of memory for the DMA ethernet buffers
@@ -1488,7 +1508,7 @@ err_out_unregister_netdev:
platform_set_drvdata(pdev, NULL);
unregister_netdev(ndev);
err_out_dma_unmap:
- if (!use_iram_for_net() ||
+ if (!use_iram_for_net(&pldat->pdev->dev) ||
pldat->dma_buff_size > lpc32xx_return_iram_size())
dma_free_coherent(&pldat->pdev->dev, pldat->dma_buff_size,
pldat->dma_buff_base_v,
@@ -1515,7 +1535,7 @@ static int lpc_eth_drv_remove(struct platform_device *pdev)
unregister_netdev(ndev);
platform_set_drvdata(pdev, NULL);
- if (!use_iram_for_net() ||
+ if (!use_iram_for_net(&pldat->pdev->dev) ||
pldat->dma_buff_size > lpc32xx_return_iram_size())
dma_free_coherent(&pldat->pdev->dev, pldat->dma_buff_size,
pldat->dma_buff_base_v,
@@ -1584,6 +1604,14 @@ static int lpc_eth_drv_resume(struct platform_device *pdev)
}
#endif
+#ifdef CONFIG_OF
+static const struct of_device_id lpc_eth_match[] = {
+ { .compatible = "nxp,lpc-eth" },
+ { }
+};
+MODULE_DEVICE_TABLE(of, lpc_eth_match);
+#endif
+
static struct platform_driver lpc_eth_driver = {
.probe = lpc_eth_drv_probe,
.remove = __devexit_p(lpc_eth_drv_remove),
@@ -1593,6 +1621,7 @@ static struct platform_driver lpc_eth_driver = {
#endif
.driver = {
.name = MODNAME,
+ .of_match_table = of_match_ptr(lpc_eth_match),
},
};
diff --git a/drivers/net/ethernet/qlogic/netxen/netxen_nic_init.c b/drivers/net/ethernet/qlogic/netxen/netxen_nic_init.c
index 0d725dc91bcb..8694124ef77d 100644
--- a/drivers/net/ethernet/qlogic/netxen/netxen_nic_init.c
+++ b/drivers/net/ethernet/qlogic/netxen/netxen_nic_init.c
@@ -1260,8 +1260,7 @@ next:
void
netxen_release_firmware(struct netxen_adapter *adapter)
{
- if (adapter->fw)
- release_firmware(adapter->fw);
+ release_firmware(adapter->fw);
adapter->fw = NULL;
}
diff --git a/drivers/net/ethernet/qlogic/qlcnic/qlcnic_init.c b/drivers/net/ethernet/qlogic/qlcnic/qlcnic_init.c
index d32cf0ddf1b9..799fd40ed03a 100644
--- a/drivers/net/ethernet/qlogic/qlcnic/qlcnic_init.c
+++ b/drivers/net/ethernet/qlogic/qlcnic/qlcnic_init.c
@@ -1321,8 +1321,7 @@ next:
void
qlcnic_release_firmware(struct qlcnic_adapter *adapter)
{
- if (adapter->fw)
- release_firmware(adapter->fw);
+ release_firmware(adapter->fw);
adapter->fw = NULL;
}
diff --git a/drivers/net/ethernet/realtek/r8169.c b/drivers/net/ethernet/realtek/r8169.c
index 4f74b9762c29..00b4f56a671c 100644
--- a/drivers/net/ethernet/realtek/r8169.c
+++ b/drivers/net/ethernet/realtek/r8169.c
@@ -6051,7 +6051,7 @@ static int rtl_open(struct net_device *dev)
pm_runtime_get_sync(&pdev->dev);
/*
- * Rx and Tx desscriptors needs 256 bytes alignment.
+ * Rx and Tx descriptors needs 256 bytes alignment.
* dma_alloc_coherent provides more.
*/
tp->TxDescArray = dma_alloc_coherent(&pdev->dev, R8169_TX_RING_BYTES,
diff --git a/drivers/net/ethernet/s6gmac.c b/drivers/net/ethernet/s6gmac.c
index 8e9fda0c7aeb..2ed3ab4b3c2d 100644
--- a/drivers/net/ethernet/s6gmac.c
+++ b/drivers/net/ethernet/s6gmac.c
@@ -1,7 +1,7 @@
/*
* Ethernet driver for S6105 on chip network device
* (c)2008 emlix GmbH http://www.emlix.com
- * Authors: Oskar Schirmer <os@emlix.com>
+ * Authors: Oskar Schirmer <oskar@scara.com>
* Daniel Gloeckner <dg@emlix.com>
*
* This program is free software; you can redistribute it and/or
@@ -1070,4 +1070,4 @@ module_exit(s6gmac_exit);
MODULE_LICENSE("GPL");
MODULE_DESCRIPTION("S6105 on chip Ethernet driver");
-MODULE_AUTHOR("Oskar Schirmer <os@emlix.com>");
+MODULE_AUTHOR("Oskar Schirmer <oskar@scara.com>");
diff --git a/drivers/net/ethernet/tehuti/tehuti.c b/drivers/net/ethernet/tehuti/tehuti.c
index 8846516678c3..447a6932cab3 100644
--- a/drivers/net/ethernet/tehuti/tehuti.c
+++ b/drivers/net/ethernet/tehuti/tehuti.c
@@ -341,8 +341,8 @@ static int bdx_fw_load(struct bdx_priv *priv)
out:
if (master)
WRITE_REG(priv, regINIT_SEMAPHORE, 1);
- if (fw)
- release_firmware(fw);
+
+ release_firmware(fw);
if (rc) {
netdev_err(priv->ndev, "firmware loading failed\n");
diff --git a/drivers/net/irda/Kconfig b/drivers/net/irda/Kconfig
index 35758445297e..595205406d73 100644
--- a/drivers/net/irda/Kconfig
+++ b/drivers/net/irda/Kconfig
@@ -211,8 +211,8 @@ config KINGSUN_DONGLE
kingsun-sir.
config EP7211_DONGLE
- tristate "EP7211 I/R support"
- depends on IRTTY_SIR && ARCH_EP7211 && IRDA && EXPERIMENTAL
+ tristate "Cirrus Logic clps711x I/R support"
+ depends on IRTTY_SIR && ARCH_CLPS711X && IRDA && EXPERIMENTAL
help
Say Y here if you want to build support for the Cirrus logic
EP7211 chipset's infrared module.
@@ -316,7 +316,7 @@ config AU1000_FIR
tristate "Alchemy IrDA SIR/FIR"
depends on IRDA && MIPS_ALCHEMY
help
- Say Y/M here to build suppor the the IrDA peripheral on the
+ Say Y/M here to build support the IrDA peripheral on the
Alchemy Au1000 and Au1100 SoCs.
Say M to build a module; it will be called au1k_ir.ko
diff --git a/drivers/net/irda/irda-usb.c b/drivers/net/irda/irda-usb.c
index 72f687b40d66..f9a86bdb12fa 100644
--- a/drivers/net/irda/irda-usb.c
+++ b/drivers/net/irda/irda-usb.c
@@ -1671,7 +1671,7 @@ static int irda_usb_probe(struct usb_interface *intf,
/* Is this really necessary? (no, except maybe for broken devices) */
if (usb_reset_configuration (dev) < 0) {
- err("reset_configuration failed");
+ dev_err(&intf->dev, "reset_configuration failed\n");
ret = -EIO;
goto err_out_3;
}
diff --git a/drivers/net/irda/kingsun-sir.c b/drivers/net/irda/kingsun-sir.c
index 79aebeee928c..7b4833874ef5 100644
--- a/drivers/net/irda/kingsun-sir.c
+++ b/drivers/net/irda/kingsun-sir.c
@@ -134,14 +134,16 @@ static void kingsun_send_irq(struct urb *urb)
/* in process of stopping, just drop data */
if (!netif_running(kingsun->netdev)) {
- err("kingsun_send_irq: Network not running!");
+ dev_err(&kingsun->usbdev->dev,
+ "kingsun_send_irq: Network not running!\n");
return;
}
/* unlink, shutdown, unplug, other nasties */
if (urb->status != 0) {
- err("kingsun_send_irq: urb asynchronously failed - %d",
- urb->status);
+ dev_err(&kingsun->usbdev->dev,
+ "kingsun_send_irq: urb asynchronously failed - %d\n",
+ urb->status);
}
netif_wake_queue(netdev);
}
@@ -177,7 +179,8 @@ static netdev_tx_t kingsun_hard_xmit(struct sk_buff *skb,
kingsun, 1);
if ((ret = usb_submit_urb(kingsun->tx_urb, GFP_ATOMIC))) {
- err("kingsun_hard_xmit: failed tx_urb submit: %d", ret);
+ dev_err(&kingsun->usbdev->dev,
+ "kingsun_hard_xmit: failed tx_urb submit: %d\n", ret);
switch (ret) {
case -ENODEV:
case -EPIPE:
@@ -211,8 +214,9 @@ static void kingsun_rcv_irq(struct urb *urb)
/* unlink, shutdown, unplug, other nasties */
if (urb->status != 0) {
- err("kingsun_rcv_irq: urb asynchronously failed - %d",
- urb->status);
+ dev_err(&kingsun->usbdev->dev,
+ "kingsun_rcv_irq: urb asynchronously failed - %d\n",
+ urb->status);
kingsun->receiving = 0;
return;
}
@@ -238,8 +242,9 @@ static void kingsun_rcv_irq(struct urb *urb)
? 1 : 0;
}
} else if (urb->actual_length > 0) {
- err("%s(): Unexpected response length, expected %d got %d",
- __func__, kingsun->max_rx, urb->actual_length);
+ dev_err(&kingsun->usbdev->dev,
+ "%s(): Unexpected response length, expected %d got %d\n",
+ __func__, kingsun->max_rx, urb->actual_length);
}
/* This urb has already been filled in kingsun_net_open */
ret = usb_submit_urb(urb, GFP_ATOMIC);
@@ -286,7 +291,7 @@ static int kingsun_net_open(struct net_device *netdev)
sprintf(hwname, "usb#%d", kingsun->usbdev->devnum);
kingsun->irlap = irlap_open(netdev, &kingsun->qos, hwname);
if (!kingsun->irlap) {
- err("kingsun-sir: irlap_open failed");
+ dev_err(&kingsun->usbdev->dev, "irlap_open failed\n");
goto free_mem;
}
@@ -298,7 +303,8 @@ static int kingsun_net_open(struct net_device *netdev)
kingsun->rx_urb->status = 0;
err = usb_submit_urb(kingsun->rx_urb, GFP_KERNEL);
if (err) {
- err("kingsun-sir: first urb-submit failed: %d", err);
+ dev_err(&kingsun->usbdev->dev,
+ "first urb-submit failed: %d\n", err);
goto close_irlap;
}
@@ -446,13 +452,15 @@ static int kingsun_probe(struct usb_interface *intf,
*/
interface = intf->cur_altsetting;
if (interface->desc.bNumEndpoints != 2) {
- err("kingsun-sir: expected 2 endpoints, found %d",
- interface->desc.bNumEndpoints);
+ dev_err(&intf->dev,
+ "kingsun-sir: expected 2 endpoints, found %d\n",
+ interface->desc.bNumEndpoints);
return -ENODEV;
}
endpoint = &interface->endpoint[KINGSUN_EP_IN].desc;
if (!usb_endpoint_is_int_in(endpoint)) {
- err("kingsun-sir: endpoint 0 is not interrupt IN");
+ dev_err(&intf->dev,
+ "kingsun-sir: endpoint 0 is not interrupt IN\n");
return -ENODEV;
}
@@ -460,14 +468,16 @@ static int kingsun_probe(struct usb_interface *intf,
pipe = usb_rcvintpipe(dev, ep_in);
maxp_in = usb_maxpacket(dev, pipe, usb_pipeout(pipe));
if (maxp_in > 255 || maxp_in <= 1) {
- err("%s: endpoint 0 has max packet size %d not in range",
- __FILE__, maxp_in);
+ dev_err(&intf->dev,
+ "endpoint 0 has max packet size %d not in range\n",
+ maxp_in);
return -ENODEV;
}
endpoint = &interface->endpoint[KINGSUN_EP_OUT].desc;
if (!usb_endpoint_is_int_out(endpoint)) {
- err("kingsun-sir: endpoint 1 is not interrupt OUT");
+ dev_err(&intf->dev,
+ "kingsun-sir: endpoint 1 is not interrupt OUT\n");
return -ENODEV;
}
diff --git a/drivers/net/irda/ks959-sir.c b/drivers/net/irda/ks959-sir.c
index abe689dffc72..824e2a93fe8a 100644
--- a/drivers/net/irda/ks959-sir.c
+++ b/drivers/net/irda/ks959-sir.c
@@ -247,8 +247,9 @@ static void ks959_speed_irq(struct urb *urb)
{
/* unlink, shutdown, unplug, other nasties */
if (urb->status != 0) {
- err("ks959_speed_irq: urb asynchronously failed - %d",
- urb->status);
+ dev_err(&urb->dev->dev,
+ "ks959_speed_irq: urb asynchronously failed - %d\n",
+ urb->status);
}
}
@@ -332,14 +333,16 @@ static void ks959_send_irq(struct urb *urb)
/* in process of stopping, just drop data */
if (!netif_running(kingsun->netdev)) {
- err("ks959_send_irq: Network not running!");
+ dev_err(&kingsun->usbdev->dev,
+ "ks959_send_irq: Network not running!\n");
return;
}
/* unlink, shutdown, unplug, other nasties */
if (urb->status != 0) {
- err("ks959_send_irq: urb asynchronously failed - %d",
- urb->status);
+ dev_err(&kingsun->usbdev->dev,
+ "ks959_send_irq: urb asynchronously failed - %d\n",
+ urb->status);
return;
}
@@ -358,8 +361,9 @@ static void ks959_send_irq(struct urb *urb)
if (kingsun->tx_buf_clear_used > 0) {
/* There is more data to be sent */
if ((ret = ks959_submit_tx_fragment(kingsun)) != 0) {
- err("ks959_send_irq: failed tx_urb submit: %d",
- ret);
+ dev_err(&kingsun->usbdev->dev,
+ "ks959_send_irq: failed tx_urb submit: %d\n",
+ ret);
switch (ret) {
case -ENODEV:
case -EPIPE:
@@ -407,7 +411,8 @@ static netdev_tx_t ks959_hard_xmit(struct sk_buff *skb,
kingsun->tx_buf_clear_used = wraplen;
if ((ret = ks959_submit_tx_fragment(kingsun)) != 0) {
- err("ks959_hard_xmit: failed tx_urb submit: %d", ret);
+ dev_err(&kingsun->usbdev->dev,
+ "ks959_hard_xmit: failed tx_urb submit: %d\n", ret);
switch (ret) {
case -ENODEV:
case -EPIPE:
@@ -442,8 +447,9 @@ static void ks959_rcv_irq(struct urb *urb)
/* unlink, shutdown, unplug, other nasties */
if (urb->status != 0) {
- err("kingsun_rcv_irq: urb asynchronously failed - %d",
- urb->status);
+ dev_err(&kingsun->usbdev->dev,
+ "kingsun_rcv_irq: urb asynchronously failed - %d\n",
+ urb->status);
kingsun->receiving = 0;
return;
}
@@ -536,7 +542,7 @@ static int ks959_net_open(struct net_device *netdev)
sprintf(hwname, "usb#%d", kingsun->usbdev->devnum);
kingsun->irlap = irlap_open(netdev, &kingsun->qos, hwname);
if (!kingsun->irlap) {
- err("ks959-sir: irlap_open failed");
+ dev_err(&kingsun->usbdev->dev, "irlap_open failed\n");
goto free_mem;
}
@@ -549,7 +555,8 @@ static int ks959_net_open(struct net_device *netdev)
kingsun->rx_urb->status = 0;
err = usb_submit_urb(kingsun->rx_urb, GFP_KERNEL);
if (err) {
- err("ks959-sir: first urb-submit failed: %d", err);
+ dev_err(&kingsun->usbdev->dev,
+ "first urb-submit failed: %d\n", err);
goto close_irlap;
}
diff --git a/drivers/net/irda/ksdazzle-sir.c b/drivers/net/irda/ksdazzle-sir.c
index f8c01088eeb7..5a278ab83c2f 100644
--- a/drivers/net/irda/ksdazzle-sir.c
+++ b/drivers/net/irda/ksdazzle-sir.c
@@ -168,10 +168,10 @@ struct ksdazzle_cb {
static void ksdazzle_speed_irq(struct urb *urb)
{
/* unlink, shutdown, unplug, other nasties */
- if (urb->status != 0) {
- err("ksdazzle_speed_irq: urb asynchronously failed - %d",
- urb->status);
- }
+ if (urb->status != 0)
+ dev_err(&urb->dev->dev,
+ "ksdazzle_speed_irq: urb asynchronously failed - %d\n",
+ urb->status);
}
/* Send a control request to change speed of the dongle */
@@ -245,14 +245,16 @@ static void ksdazzle_send_irq(struct urb *urb)
/* in process of stopping, just drop data */
if (!netif_running(kingsun->netdev)) {
- err("ksdazzle_send_irq: Network not running!");
+ dev_err(&kingsun->usbdev->dev,
+ "ksdazzle_send_irq: Network not running!\n");
return;
}
/* unlink, shutdown, unplug, other nasties */
if (urb->status != 0) {
- err("ksdazzle_send_irq: urb asynchronously failed - %d",
- urb->status);
+ dev_err(&kingsun->usbdev->dev,
+ "ksdazzle_send_irq: urb asynchronously failed - %d\n",
+ urb->status);
return;
}
@@ -271,7 +273,9 @@ static void ksdazzle_send_irq(struct urb *urb)
if (kingsun->tx_buf_clear_used > 0) {
/* There is more data to be sent */
if ((ret = ksdazzle_submit_tx_fragment(kingsun)) != 0) {
- err("ksdazzle_send_irq: failed tx_urb submit: %d", ret);
+ dev_err(&kingsun->usbdev->dev,
+ "ksdazzle_send_irq: failed tx_urb submit: %d\n",
+ ret);
switch (ret) {
case -ENODEV:
case -EPIPE:
@@ -320,7 +324,8 @@ static netdev_tx_t ksdazzle_hard_xmit(struct sk_buff *skb,
kingsun->tx_buf_clear_used = wraplen;
if ((ret = ksdazzle_submit_tx_fragment(kingsun)) != 0) {
- err("ksdazzle_hard_xmit: failed tx_urb submit: %d", ret);
+ dev_err(&kingsun->usbdev->dev,
+ "ksdazzle_hard_xmit: failed tx_urb submit: %d\n", ret);
switch (ret) {
case -ENODEV:
case -EPIPE:
@@ -355,8 +360,9 @@ static void ksdazzle_rcv_irq(struct urb *urb)
/* unlink, shutdown, unplug, other nasties */
if (urb->status != 0) {
- err("ksdazzle_rcv_irq: urb asynchronously failed - %d",
- urb->status);
+ dev_err(&kingsun->usbdev->dev,
+ "ksdazzle_rcv_irq: urb asynchronously failed - %d\n",
+ urb->status);
kingsun->receiving = 0;
return;
}
@@ -430,7 +436,7 @@ static int ksdazzle_net_open(struct net_device *netdev)
sprintf(hwname, "usb#%d", kingsun->usbdev->devnum);
kingsun->irlap = irlap_open(netdev, &kingsun->qos, hwname);
if (!kingsun->irlap) {
- err("ksdazzle-sir: irlap_open failed");
+ dev_err(&kingsun->usbdev->dev, "irlap_open failed\n");
goto free_mem;
}
@@ -442,7 +448,7 @@ static int ksdazzle_net_open(struct net_device *netdev)
kingsun->rx_urb->status = 0;
err = usb_submit_urb(kingsun->rx_urb, GFP_KERNEL);
if (err) {
- err("ksdazzle-sir: first urb-submit failed: %d", err);
+ dev_err(&kingsun->usbdev->dev, "first urb-submit failed: %d\n", err);
goto close_irlap;
}
@@ -590,13 +596,14 @@ static int ksdazzle_probe(struct usb_interface *intf,
*/
interface = intf->cur_altsetting;
if (interface->desc.bNumEndpoints != 2) {
- err("ksdazzle: expected 2 endpoints, found %d",
- interface->desc.bNumEndpoints);
+ dev_err(&intf->dev, "ksdazzle: expected 2 endpoints, found %d\n",
+ interface->desc.bNumEndpoints);
return -ENODEV;
}
endpoint = &interface->endpoint[KINGSUN_EP_IN].desc;
if (!usb_endpoint_is_int_in(endpoint)) {
- err("ksdazzle: endpoint 0 is not interrupt IN");
+ dev_err(&intf->dev,
+ "ksdazzle: endpoint 0 is not interrupt IN\n");
return -ENODEV;
}
@@ -604,13 +611,16 @@ static int ksdazzle_probe(struct usb_interface *intf,
pipe = usb_rcvintpipe(dev, ep_in);
maxp_in = usb_maxpacket(dev, pipe, usb_pipeout(pipe));
if (maxp_in > 255 || maxp_in <= 1) {
- err("ksdazzle: endpoint 0 has max packet size %d not in range [2..255]", maxp_in);
+ dev_err(&intf->dev,
+ "ksdazzle: endpoint 0 has max packet size %d not in range [2..255]\n",
+ maxp_in);
return -ENODEV;
}
endpoint = &interface->endpoint[KINGSUN_EP_OUT].desc;
if (!usb_endpoint_is_int_out(endpoint)) {
- err("ksdazzle: endpoint 1 is not interrupt OUT");
+ dev_err(&intf->dev,
+ "ksdazzle: endpoint 1 is not interrupt OUT\n");
return -ENODEV;
}
diff --git a/drivers/net/irda/stir4200.c b/drivers/net/irda/stir4200.c
index e6e59a078ef4..876e709b65ba 100644
--- a/drivers/net/irda/stir4200.c
+++ b/drivers/net/irda/stir4200.c
@@ -904,7 +904,7 @@ static int stir_net_open(struct net_device *netdev)
sprintf(hwname, "usb#%d", stir->usbdev->devnum);
stir->irlap = irlap_open(netdev, &stir->qos, hwname);
if (!stir->irlap) {
- err("stir4200: irlap_open failed");
+ dev_err(&stir->usbdev->dev, "irlap_open failed\n");
goto err_out5;
}
@@ -913,7 +913,7 @@ static int stir_net_open(struct net_device *netdev)
"%s", stir->netdev->name);
if (IS_ERR(stir->thread)) {
err = PTR_ERR(stir->thread);
- err("stir4200: unable to start kernel thread");
+ dev_err(&stir->usbdev->dev, "unable to start kernel thread\n");
goto err_out6;
}
@@ -1042,7 +1042,7 @@ static int stir_probe(struct usb_interface *intf,
ret = usb_reset_configuration(dev);
if (ret != 0) {
- err("stir4200: usb reset configuration failed");
+ dev_err(&intf->dev, "usb reset configuration failed\n");
goto err_out2;
}
diff --git a/drivers/net/usb/asix.c b/drivers/net/usb/asix.c
index 42b5151aa78a..71e2b0523bc2 100644
--- a/drivers/net/usb/asix.c
+++ b/drivers/net/usb/asix.c
@@ -1647,6 +1647,7 @@ static struct usb_driver asix_driver = {
.resume = usbnet_resume,
.disconnect = usbnet_disconnect,
.supports_autosuspend = 1,
+ .disable_hub_initiated_lpm = 1,
};
module_usb_driver(asix_driver);
diff --git a/drivers/net/usb/catc.c b/drivers/net/usb/catc.c
index 182cfb4aeb1d..26c5bebd9eca 100644
--- a/drivers/net/usb/catc.c
+++ b/drivers/net/usb/catc.c
@@ -338,16 +338,18 @@ static void catc_irq_done(struct urb *urb)
} else {
catc->rx_urb->dev = catc->usbdev;
if ((res = usb_submit_urb(catc->rx_urb, GFP_ATOMIC)) < 0) {
- err("submit(rx_urb) status %d", res);
+ dev_err(&catc->usbdev->dev,
+ "submit(rx_urb) status %d\n", res);
}
}
}
resubmit:
res = usb_submit_urb (urb, GFP_ATOMIC);
if (res)
- err ("can't resubmit intr, %s-%s, status %d",
- catc->usbdev->bus->bus_name,
- catc->usbdev->devpath, res);
+ dev_err(&catc->usbdev->dev,
+ "can't resubmit intr, %s-%s, status %d\n",
+ catc->usbdev->bus->bus_name,
+ catc->usbdev->devpath, res);
}
/*
@@ -366,7 +368,8 @@ static int catc_tx_run(struct catc *catc)
catc->tx_urb->dev = catc->usbdev;
if ((status = usb_submit_urb(catc->tx_urb, GFP_ATOMIC)) < 0)
- err("submit(tx_urb), status %d", status);
+ dev_err(&catc->usbdev->dev, "submit(tx_urb), status %d\n",
+ status);
catc->tx_idx = !catc->tx_idx;
catc->tx_ptr = 0;
@@ -496,7 +499,8 @@ static void catc_ctrl_run(struct catc *catc)
memcpy(catc->ctrl_buf, q->buf, q->len);
if ((status = usb_submit_urb(catc->ctrl_urb, GFP_ATOMIC)))
- err("submit(ctrl_urb) status %d", status);
+ dev_err(&catc->usbdev->dev, "submit(ctrl_urb) status %d\n",
+ status);
}
static void catc_ctrl_done(struct urb *urb)
@@ -555,7 +559,7 @@ static int catc_ctrl_async(struct catc *catc, u8 dir, u8 request, u16 value,
catc->ctrl_head = (catc->ctrl_head + 1) & (CTRL_QUEUE - 1);
if (catc->ctrl_head == catc->ctrl_tail) {
- err("ctrl queue full");
+ dev_err(&catc->usbdev->dev, "ctrl queue full\n");
catc->ctrl_tail = (catc->ctrl_tail + 1) & (CTRL_QUEUE - 1);
retval = -1;
}
@@ -714,7 +718,8 @@ static int catc_open(struct net_device *netdev)
catc->irq_urb->dev = catc->usbdev;
if ((status = usb_submit_urb(catc->irq_urb, GFP_KERNEL)) < 0) {
- err("submit(irq_urb) status %d", status);
+ dev_err(&catc->usbdev->dev, "submit(irq_urb) status %d\n",
+ status);
return -1;
}
@@ -769,7 +774,7 @@ static int catc_probe(struct usb_interface *intf, const struct usb_device_id *id
if (usb_set_interface(usbdev,
intf->altsetting->desc.bInterfaceNumber, 1)) {
- err("Can't set altsetting 1.");
+ dev_err(&intf->dev, "Can't set altsetting 1.\n");
return -EIO;
}
@@ -799,7 +804,7 @@ static int catc_probe(struct usb_interface *intf, const struct usb_device_id *id
catc->irq_urb = usb_alloc_urb(0, GFP_KERNEL);
if ((!catc->ctrl_urb) || (!catc->tx_urb) ||
(!catc->rx_urb) || (!catc->irq_urb)) {
- err("No free urbs available.");
+ dev_err(&intf->dev, "No free urbs available.\n");
usb_free_urb(catc->ctrl_urb);
usb_free_urb(catc->tx_urb);
usb_free_urb(catc->rx_urb);
@@ -947,6 +952,7 @@ static struct usb_driver catc_driver = {
.probe = catc_probe,
.disconnect = catc_disconnect,
.id_table = catc_id_table,
+ .disable_hub_initiated_lpm = 1,
};
module_usb_driver(catc_driver);
diff --git a/drivers/net/usb/cdc-phonet.c b/drivers/net/usb/cdc-phonet.c
index 3e41b00c6806..d848d4dd5754 100644
--- a/drivers/net/usb/cdc-phonet.c
+++ b/drivers/net/usb/cdc-phonet.c
@@ -457,6 +457,7 @@ static struct usb_driver usbpn_driver = {
.probe = usbpn_probe,
.disconnect = usbpn_disconnect,
.id_table = usbpn_ids,
+ .disable_hub_initiated_lpm = 1,
};
module_usb_driver(usbpn_driver);
diff --git a/drivers/net/usb/cdc_eem.c b/drivers/net/usb/cdc_eem.c
index 685a4e22c768..434d5af8e6fb 100644
--- a/drivers/net/usb/cdc_eem.c
+++ b/drivers/net/usb/cdc_eem.c
@@ -368,6 +368,7 @@ static struct usb_driver eem_driver = {
.disconnect = usbnet_disconnect,
.suspend = usbnet_suspend,
.resume = usbnet_resume,
+ .disable_hub_initiated_lpm = 1,
};
module_usb_driver(eem_driver);
diff --git a/drivers/net/usb/cdc_ether.c b/drivers/net/usb/cdc_ether.c
index fffee6aee8bb..a03de7197049 100644
--- a/drivers/net/usb/cdc_ether.c
+++ b/drivers/net/usb/cdc_ether.c
@@ -705,6 +705,7 @@ static struct usb_driver cdc_driver = {
.resume = usbnet_resume,
.reset_resume = usbnet_resume,
.supports_autosuspend = 1,
+ .disable_hub_initiated_lpm = 1,
};
module_usb_driver(cdc_driver);
diff --git a/drivers/net/usb/cdc_ncm.c b/drivers/net/usb/cdc_ncm.c
index 7adc9f6b0ea1..4b9513fcf275 100644
--- a/drivers/net/usb/cdc_ncm.c
+++ b/drivers/net/usb/cdc_ncm.c
@@ -1212,6 +1212,7 @@ static struct usb_driver cdc_ncm_driver = {
.resume = usbnet_resume,
.reset_resume = usbnet_resume,
.supports_autosuspend = 1,
+ .disable_hub_initiated_lpm = 1,
};
static const struct ethtool_ops cdc_ncm_ethtool_ops = {
diff --git a/drivers/net/usb/cdc_subset.c b/drivers/net/usb/cdc_subset.c
index b403d934e4e3..0d1fe89ae0bd 100644
--- a/drivers/net/usb/cdc_subset.c
+++ b/drivers/net/usb/cdc_subset.c
@@ -336,6 +336,7 @@ static struct usb_driver cdc_subset_driver = {
.resume = usbnet_resume,
.disconnect = usbnet_disconnect,
.id_table = products,
+ .disable_hub_initiated_lpm = 1,
};
module_usb_driver(cdc_subset_driver);
diff --git a/drivers/net/usb/cx82310_eth.c b/drivers/net/usb/cx82310_eth.c
index 0e0531356e62..49ab45e17fe8 100644
--- a/drivers/net/usb/cx82310_eth.c
+++ b/drivers/net/usb/cx82310_eth.c
@@ -327,6 +327,7 @@ static struct usb_driver cx82310_driver = {
.disconnect = usbnet_disconnect,
.suspend = usbnet_suspend,
.resume = usbnet_resume,
+ .disable_hub_initiated_lpm = 1,
};
module_usb_driver(cx82310_driver);
diff --git a/drivers/net/usb/dm9601.c b/drivers/net/usb/dm9601.c
index b97226318ea5..e0433ce6ced7 100644
--- a/drivers/net/usb/dm9601.c
+++ b/drivers/net/usb/dm9601.c
@@ -670,6 +670,7 @@ static struct usb_driver dm9601_driver = {
.disconnect = usbnet_disconnect,
.suspend = usbnet_suspend,
.resume = usbnet_resume,
+ .disable_hub_initiated_lpm = 1,
};
module_usb_driver(dm9601_driver);
diff --git a/drivers/net/usb/gl620a.c b/drivers/net/usb/gl620a.c
index 38266bdae26b..db3c8021f2a3 100644
--- a/drivers/net/usb/gl620a.c
+++ b/drivers/net/usb/gl620a.c
@@ -225,6 +225,7 @@ static struct usb_driver gl620a_driver = {
.disconnect = usbnet_disconnect,
.suspend = usbnet_suspend,
.resume = usbnet_resume,
+ .disable_hub_initiated_lpm = 1,
};
module_usb_driver(gl620a_driver);
diff --git a/drivers/net/usb/hso.c b/drivers/net/usb/hso.c
index 2d2a6882ba33..62f30b46fa42 100644
--- a/drivers/net/usb/hso.c
+++ b/drivers/net/usb/hso.c
@@ -106,13 +106,6 @@
#define MAX_RX_URBS 2
-static inline struct hso_serial *get_serial_by_tty(struct tty_struct *tty)
-{
- if (tty)
- return tty->driver_data;
- return NULL;
-}
-
/*****************************************************************************/
/* Debugging functions */
/*****************************************************************************/
@@ -255,9 +248,8 @@ struct hso_serial {
u8 dtr_state;
unsigned tx_urb_used:1;
+ struct tty_port port;
/* from usb_serial_port */
- struct tty_struct *tty;
- int open_count;
spinlock_t serial_lock;
int (*write_data) (struct hso_serial *serial);
@@ -1114,7 +1106,7 @@ static void hso_init_termios(struct ktermios *termios)
static void _hso_serial_set_termios(struct tty_struct *tty,
struct ktermios *old)
{
- struct hso_serial *serial = get_serial_by_tty(tty);
+ struct hso_serial *serial = tty->driver_data;
struct ktermios *termios;
if (!serial) {
@@ -1190,7 +1182,7 @@ static void put_rxbuf_data_and_resubmit_ctrl_urb(struct hso_serial *serial)
struct urb *urb;
urb = serial->rx_urb[0];
- if (serial->open_count > 0) {
+ if (serial->port.count > 0) {
count = put_rxbuf_data(urb, serial);
if (count == -1)
return;
@@ -1226,7 +1218,7 @@ static void hso_std_serial_read_bulk_callback(struct urb *urb)
DUMP1(urb->transfer_buffer, urb->actual_length);
/* Anyone listening? */
- if (serial->open_count == 0)
+ if (serial->port.count == 0)
return;
if (status == 0) {
@@ -1268,7 +1260,7 @@ static void hso_unthrottle_tasklet(struct hso_serial *serial)
static void hso_unthrottle(struct tty_struct *tty)
{
- struct hso_serial *serial = get_serial_by_tty(tty);
+ struct hso_serial *serial = tty->driver_data;
tasklet_hi_schedule(&serial->unthrottle_tasklet);
}
@@ -1304,15 +1296,12 @@ static int hso_serial_open(struct tty_struct *tty, struct file *filp)
kref_get(&serial->parent->ref);
/* setup */
- spin_lock_irq(&serial->serial_lock);
tty->driver_data = serial;
- tty_kref_put(serial->tty);
- serial->tty = tty_kref_get(tty);
- spin_unlock_irq(&serial->serial_lock);
+ tty_port_tty_set(&serial->port, tty);
/* check for port already opened, if not set the termios */
- serial->open_count++;
- if (serial->open_count == 1) {
+ serial->port.count++;
+ if (serial->port.count == 1) {
serial->rx_state = RX_IDLE;
/* Force default termio settings */
_hso_serial_set_termios(tty, NULL);
@@ -1324,7 +1313,7 @@ static int hso_serial_open(struct tty_struct *tty, struct file *filp)
result = hso_start_serial_device(serial->parent, GFP_KERNEL);
if (result) {
hso_stop_serial_device(serial->parent);
- serial->open_count--;
+ serial->port.count--;
kref_put(&serial->parent->ref, hso_serial_ref_free);
}
} else {
@@ -1361,17 +1350,11 @@ static void hso_serial_close(struct tty_struct *tty, struct file *filp)
/* reset the rts and dtr */
/* do the actual close */
- serial->open_count--;
+ serial->port.count--;
- if (serial->open_count <= 0) {
- serial->open_count = 0;
- spin_lock_irq(&serial->serial_lock);
- if (serial->tty == tty) {
- serial->tty->driver_data = NULL;
- serial->tty = NULL;
- tty_kref_put(tty);
- }
- spin_unlock_irq(&serial->serial_lock);
+ if (serial->port.count <= 0) {
+ serial->port.count = 0;
+ tty_port_tty_set(&serial->port, NULL);
if (!usb_gone)
hso_stop_serial_device(serial->parent);
tasklet_kill(&serial->unthrottle_tasklet);
@@ -1390,7 +1373,7 @@ static void hso_serial_close(struct tty_struct *tty, struct file *filp)
static int hso_serial_write(struct tty_struct *tty, const unsigned char *buf,
int count)
{
- struct hso_serial *serial = get_serial_by_tty(tty);
+ struct hso_serial *serial = tty->driver_data;
int space, tx_bytes;
unsigned long flags;
@@ -1422,7 +1405,7 @@ out:
/* how much room is there for writing */
static int hso_serial_write_room(struct tty_struct *tty)
{
- struct hso_serial *serial = get_serial_by_tty(tty);
+ struct hso_serial *serial = tty->driver_data;
int room;
unsigned long flags;
@@ -1437,7 +1420,7 @@ static int hso_serial_write_room(struct tty_struct *tty)
/* setup the term */
static void hso_serial_set_termios(struct tty_struct *tty, struct ktermios *old)
{
- struct hso_serial *serial = get_serial_by_tty(tty);
+ struct hso_serial *serial = tty->driver_data;
unsigned long flags;
if (old)
@@ -1446,7 +1429,7 @@ static void hso_serial_set_termios(struct tty_struct *tty, struct ktermios *old)
/* the actual setup */
spin_lock_irqsave(&serial->serial_lock, flags);
- if (serial->open_count)
+ if (serial->port.count)
_hso_serial_set_termios(tty, old);
else
tty->termios = old;
@@ -1458,7 +1441,7 @@ static void hso_serial_set_termios(struct tty_struct *tty, struct ktermios *old)
/* how many characters in the buffer */
static int hso_serial_chars_in_buffer(struct tty_struct *tty)
{
- struct hso_serial *serial = get_serial_by_tty(tty);
+ struct hso_serial *serial = tty->driver_data;
int chars;
unsigned long flags;
@@ -1629,7 +1612,7 @@ static int hso_get_count(struct tty_struct *tty,
struct serial_icounter_struct *icount)
{
struct uart_icount cnow;
- struct hso_serial *serial = get_serial_by_tty(tty);
+ struct hso_serial *serial = tty->driver_data;
struct hso_tiocmget *tiocmget = serial->tiocmget;
memset(icount, 0, sizeof(struct serial_icounter_struct));
@@ -1659,7 +1642,7 @@ static int hso_get_count(struct tty_struct *tty,
static int hso_serial_tiocmget(struct tty_struct *tty)
{
int retval;
- struct hso_serial *serial = get_serial_by_tty(tty);
+ struct hso_serial *serial = tty->driver_data;
struct hso_tiocmget *tiocmget;
u16 UART_state_bitmap;
@@ -1693,7 +1676,7 @@ static int hso_serial_tiocmset(struct tty_struct *tty,
int val = 0;
unsigned long flags;
int if_num;
- struct hso_serial *serial = get_serial_by_tty(tty);
+ struct hso_serial *serial = tty->driver_data;
/* sanity check */
if (!serial) {
@@ -1733,7 +1716,7 @@ static int hso_serial_tiocmset(struct tty_struct *tty,
static int hso_serial_ioctl(struct tty_struct *tty,
unsigned int cmd, unsigned long arg)
{
- struct hso_serial *serial = get_serial_by_tty(tty);
+ struct hso_serial *serial = tty->driver_data;
int ret = 0;
D4("IOCTL cmd: %d, arg: %ld", cmd, arg);
@@ -1905,7 +1888,7 @@ static void intr_callback(struct urb *urb)
D1("Pending read interrupt on port %d\n", i);
spin_lock(&serial->serial_lock);
if (serial->rx_state == RX_IDLE &&
- serial->open_count > 0) {
+ serial->port.count > 0) {
/* Setup and send a ctrl req read on
* port i */
if (!serial->rx_urb_filled[0]) {
@@ -1954,14 +1937,13 @@ static void hso_std_serial_write_bulk_callback(struct urb *urb)
spin_lock(&serial->serial_lock);
serial->tx_urb_used = 0;
- tty = tty_kref_get(serial->tty);
spin_unlock(&serial->serial_lock);
if (status) {
handle_usb_error(status, __func__, serial->parent);
- tty_kref_put(tty);
return;
}
hso_put_activity(serial->parent);
+ tty = tty_port_tty_get(&serial->port);
if (tty) {
tty_wakeup(tty);
tty_kref_put(tty);
@@ -2001,7 +1983,6 @@ static void ctrl_callback(struct urb *urb)
struct hso_serial *serial = urb->context;
struct usb_ctrlrequest *req;
int status = urb->status;
- struct tty_struct *tty;
/* sanity check */
if (!serial)
@@ -2009,11 +1990,9 @@ static void ctrl_callback(struct urb *urb)
spin_lock(&serial->serial_lock);
serial->tx_urb_used = 0;
- tty = tty_kref_get(serial->tty);
spin_unlock(&serial->serial_lock);
if (status) {
handle_usb_error(status, __func__, serial->parent);
- tty_kref_put(tty);
return;
}
@@ -2031,13 +2010,15 @@ static void ctrl_callback(struct urb *urb)
put_rxbuf_data_and_resubmit_ctrl_urb(serial);
spin_unlock(&serial->serial_lock);
} else {
+ struct tty_struct *tty = tty_port_tty_get(&serial->port);
hso_put_activity(serial->parent);
- if (tty)
+ if (tty) {
tty_wakeup(tty);
+ tty_kref_put(tty);
+ }
/* response to a write command */
hso_kick_transmit(serial);
}
- tty_kref_put(tty);
}
/* handle RX data for serial port */
@@ -2053,8 +2034,7 @@ static int put_rxbuf_data(struct urb *urb, struct hso_serial *serial)
return -2;
}
- /* All callers to put_rxbuf_data hold serial_lock */
- tty = tty_kref_get(serial->tty);
+ tty = tty_port_tty_get(&serial->port);
/* Push data to tty */
if (tty) {
@@ -2074,12 +2054,12 @@ static int put_rxbuf_data(struct urb *urb, struct hso_serial *serial)
write_length_remaining -= curr_write_len;
tty_flip_buffer_push(tty);
}
+ tty_kref_put(tty);
}
if (write_length_remaining == 0) {
serial->curr_rx_urb_offset = 0;
serial->rx_urb_filled[hso_urb_to_index(serial, urb)] = 0;
}
- tty_kref_put(tty);
return write_length_remaining;
}
@@ -2320,6 +2300,7 @@ static int hso_serial_common_create(struct hso_serial *serial, int num_urbs,
serial->minor = minor;
serial->magic = HSO_SERIAL_MAGIC;
spin_lock_init(&serial->serial_lock);
+ tty_port_init(&serial->port);
serial->num_rx_urbs = num_urbs;
/* RX, allocate urb and initialize */
@@ -3098,7 +3079,7 @@ static int hso_resume(struct usb_interface *iface)
/* Start all serial ports */
for (i = 0; i < HSO_SERIAL_TTY_MINORS; i++) {
if (serial_table[i] && (serial_table[i]->interface == iface)) {
- if (dev2ser(serial_table[i])->open_count) {
+ if (dev2ser(serial_table[i])->port.count) {
result =
hso_start_serial_device(serial_table[i], GFP_NOIO);
hso_kick_transmit(dev2ser(serial_table[i]));
@@ -3172,13 +3153,12 @@ static void hso_free_interface(struct usb_interface *interface)
if (serial_table[i] &&
(serial_table[i]->interface == interface)) {
hso_dev = dev2ser(serial_table[i]);
- spin_lock_irq(&hso_dev->serial_lock);
- tty = tty_kref_get(hso_dev->tty);
- spin_unlock_irq(&hso_dev->serial_lock);
- if (tty)
+ tty = tty_port_tty_get(&hso_dev->port);
+ if (tty) {
tty_hangup(tty);
+ tty_kref_put(tty);
+ }
mutex_lock(&hso_dev->parent->mutex);
- tty_kref_put(tty);
hso_dev->parent->usb_gone = 1;
mutex_unlock(&hso_dev->parent->mutex);
kref_put(&serial_table[i]->ref, hso_serial_ref_free);
@@ -3291,6 +3271,7 @@ static struct usb_driver hso_driver = {
.resume = hso_resume,
.reset_resume = hso_resume,
.supports_autosuspend = 1,
+ .disable_hub_initiated_lpm = 1,
};
static int __init hso_init(void)
@@ -3312,7 +3293,6 @@ static int __init hso_init(void)
return -ENOMEM;
/* fill in all needed values */
- tty_drv->magic = TTY_DRIVER_MAGIC;
tty_drv->driver_name = driver_name;
tty_drv->name = tty_filename;
@@ -3333,7 +3313,7 @@ static int __init hso_init(void)
if (result) {
printk(KERN_ERR "%s - tty_register_driver failed(%d)\n",
__func__, result);
- return result;
+ goto err_free_tty;
}
/* register this module as an usb driver */
@@ -3341,13 +3321,16 @@ static int __init hso_init(void)
if (result) {
printk(KERN_ERR "Could not register hso driver? error: %d\n",
result);
- /* cleanup serial interface */
- tty_unregister_driver(tty_drv);
- return result;
+ goto err_unreg_tty;
}
/* done */
return 0;
+err_unreg_tty:
+ tty_unregister_driver(tty_drv);
+err_free_tty:
+ put_tty_driver(tty_drv);
+ return result;
}
static void __exit hso_exit(void)
@@ -3355,6 +3338,7 @@ static void __exit hso_exit(void)
printk(KERN_INFO "hso: unloaded\n");
tty_unregister_driver(tty_drv);
+ put_tty_driver(tty_drv);
/* deregister the usb driver */
usb_deregister(&hso_driver);
}
diff --git a/drivers/net/usb/int51x1.c b/drivers/net/usb/int51x1.c
index 12a22a453ff1..8de641713d5f 100644
--- a/drivers/net/usb/int51x1.c
+++ b/drivers/net/usb/int51x1.c
@@ -236,6 +236,7 @@ static struct usb_driver int51x1_driver = {
.disconnect = usbnet_disconnect,
.suspend = usbnet_suspend,
.resume = usbnet_resume,
+ .disable_hub_initiated_lpm = 1,
};
module_usb_driver(int51x1_driver);
diff --git a/drivers/net/usb/ipheth.c b/drivers/net/usb/ipheth.c
index dd78c4cbd459..964031e3da87 100644
--- a/drivers/net/usb/ipheth.c
+++ b/drivers/net/usb/ipheth.c
@@ -209,7 +209,8 @@ static void ipheth_rcvbulk_callback(struct urb *urb)
case 0:
break;
default:
- err("%s: urb status: %d", __func__, status);
+ dev_err(&dev->intf->dev, "%s: urb status: %d\n",
+ __func__, status);
return;
}
@@ -222,7 +223,8 @@ static void ipheth_rcvbulk_callback(struct urb *urb)
skb = dev_alloc_skb(len);
if (!skb) {
- err("%s: dev_alloc_skb: -ENOMEM", __func__);
+ dev_err(&dev->intf->dev, "%s: dev_alloc_skb: -ENOMEM\n",
+ __func__);
dev->net->stats.rx_dropped++;
return;
}
@@ -251,7 +253,8 @@ static void ipheth_sndbulk_callback(struct urb *urb)
status != -ENOENT &&
status != -ECONNRESET &&
status != -ESHUTDOWN)
- err("%s: urb status: %d", __func__, status);
+ dev_err(&dev->intf->dev, "%s: urb status: %d\n",
+ __func__, status);
dev_kfree_skb_irq(dev->tx_skb);
netif_wake_queue(dev->net);
@@ -271,7 +274,8 @@ static int ipheth_carrier_set(struct ipheth_device *dev)
dev->ctrl_buf, IPHETH_CTRL_BUF_SIZE,
IPHETH_CTRL_TIMEOUT);
if (retval < 0) {
- err("%s: usb_control_msg: %d", __func__, retval);
+ dev_err(&dev->intf->dev, "%s: usb_control_msg: %d\n",
+ __func__, retval);
return retval;
}
@@ -308,9 +312,11 @@ static int ipheth_get_macaddr(struct ipheth_device *dev)
IPHETH_CTRL_BUF_SIZE,
IPHETH_CTRL_TIMEOUT);
if (retval < 0) {
- err("%s: usb_control_msg: %d", __func__, retval);
+ dev_err(&dev->intf->dev, "%s: usb_control_msg: %d\n",
+ __func__, retval);
} else if (retval < ETH_ALEN) {
- err("%s: usb_control_msg: short packet: %d bytes",
+ dev_err(&dev->intf->dev,
+ "%s: usb_control_msg: short packet: %d bytes\n",
__func__, retval);
retval = -EINVAL;
} else {
@@ -335,7 +341,8 @@ static int ipheth_rx_submit(struct ipheth_device *dev, gfp_t mem_flags)
retval = usb_submit_urb(dev->rx_urb, mem_flags);
if (retval)
- err("%s: usb_submit_urb: %d", __func__, retval);
+ dev_err(&dev->intf->dev, "%s: usb_submit_urb: %d\n",
+ __func__, retval);
return retval;
}
@@ -396,7 +403,8 @@ static int ipheth_tx(struct sk_buff *skb, struct net_device *net)
retval = usb_submit_urb(dev->tx_urb, GFP_ATOMIC);
if (retval) {
- err("%s: usb_submit_urb: %d", __func__, retval);
+ dev_err(&dev->intf->dev, "%s: usb_submit_urb: %d\n",
+ __func__, retval);
dev->net->stats.tx_errors++;
dev_kfree_skb_irq(skb);
} else {
@@ -414,7 +422,7 @@ static void ipheth_tx_timeout(struct net_device *net)
{
struct ipheth_device *dev = netdev_priv(net);
- err("%s: TX timeout", __func__);
+ dev_err(&dev->intf->dev, "%s: TX timeout\n", __func__);
dev->net->stats.tx_errors++;
usb_unlink_urb(dev->tx_urb);
}
@@ -464,7 +472,7 @@ static int ipheth_probe(struct usb_interface *intf,
hintf = usb_altnum_to_altsetting(intf, IPHETH_ALT_INTFNUM);
if (hintf == NULL) {
retval = -ENODEV;
- err("Unable to find alternate settings interface");
+ dev_err(&intf->dev, "Unable to find alternate settings interface\n");
goto err_endpoints;
}
@@ -477,7 +485,7 @@ static int ipheth_probe(struct usb_interface *intf,
}
if (!(dev->bulk_in && dev->bulk_out)) {
retval = -ENODEV;
- err("Unable to find endpoints");
+ dev_err(&intf->dev, "Unable to find endpoints\n");
goto err_endpoints;
}
@@ -495,7 +503,7 @@ static int ipheth_probe(struct usb_interface *intf,
retval = ipheth_alloc_urbs(dev);
if (retval) {
- err("error allocating urbs: %d", retval);
+ dev_err(&intf->dev, "error allocating urbs: %d\n", retval);
goto err_alloc_urbs;
}
@@ -506,7 +514,7 @@ static int ipheth_probe(struct usb_interface *intf,
retval = register_netdev(netdev);
if (retval) {
- err("error registering netdev: %d", retval);
+ dev_err(&intf->dev, "error registering netdev: %d\n", retval);
retval = -EIO;
goto err_register_netdev;
}
@@ -546,6 +554,7 @@ static struct usb_driver ipheth_driver = {
.probe = ipheth_probe,
.disconnect = ipheth_disconnect,
.id_table = ipheth_table,
+ .disable_hub_initiated_lpm = 1,
};
module_usb_driver(ipheth_driver);
diff --git a/drivers/net/usb/kalmia.c b/drivers/net/usb/kalmia.c
index 7562649b3d6b..92c49e0a59ec 100644
--- a/drivers/net/usb/kalmia.c
+++ b/drivers/net/usb/kalmia.c
@@ -372,7 +372,8 @@ static struct usb_driver kalmia_driver = {
.probe = usbnet_probe,
.disconnect = usbnet_disconnect,
.suspend = usbnet_suspend,
- .resume = usbnet_resume
+ .resume = usbnet_resume,
+ .disable_hub_initiated_lpm = 1,
};
module_usb_driver(kalmia_driver);
diff --git a/drivers/net/usb/kaweth.c b/drivers/net/usb/kaweth.c
index df2a2cf35a99..d8ad55284389 100644
--- a/drivers/net/usb/kaweth.c
+++ b/drivers/net/usb/kaweth.c
@@ -179,6 +179,7 @@ static struct usb_driver kaweth_driver = {
.resume = kaweth_resume,
.id_table = usb_klsi_table,
.supports_autosuspend = 1,
+ .disable_hub_initiated_lpm = 1,
};
typedef __u8 eth_addr_t[6];
@@ -400,12 +401,13 @@ static int kaweth_download_firmware(struct kaweth_device *kaweth,
ret = request_firmware(&fw, fwname, &kaweth->dev->dev);
if (ret) {
- err("Firmware request failed\n");
+ dev_err(&kaweth->intf->dev, "Firmware request failed\n");
return ret;
}
if (fw->size > KAWETH_FIRMWARE_BUF_SIZE) {
- err("Firmware too big: %zu", fw->size);
+ dev_err(&kaweth->intf->dev, "Firmware too big: %zu\n",
+ fw->size);
release_firmware(fw);
return -ENOSPC;
}
@@ -501,9 +503,10 @@ static void kaweth_resubmit_int_urb(struct kaweth_device *kaweth, gfp_t mf)
}
if (status)
- err ("can't resubmit intr, %s-%s, status %d",
- kaweth->dev->bus->bus_name,
- kaweth->dev->devpath, status);
+ dev_err(&kaweth->intf->dev,
+ "can't resubmit intr, %s-%s, status %d\n",
+ kaweth->dev->bus->bus_name,
+ kaweth->dev->devpath, status);
}
static void int_callback(struct urb *u)
@@ -576,7 +579,8 @@ static int kaweth_resubmit_rx_urb(struct kaweth_device *kaweth,
kaweth->suspend_lowmem_rx = 1;
schedule_delayed_work(&kaweth->lowmem_work, HZ/4);
}
- err("resubmitting rx_urb %d failed", result);
+ dev_err(&kaweth->intf->dev, "resubmitting rx_urb %d failed\n",
+ result);
} else {
kaweth->suspend_lowmem_rx = 0;
}
@@ -634,20 +638,21 @@ static void kaweth_usb_receive(struct urb *urb)
spin_unlock(&kaweth->device_lock);
if(status && status != -EREMOTEIO && count != 1) {
- err("%s RX status: %d count: %d packet_len: %d",
- net->name,
- status,
- count,
- (int)pkt_len);
+ dev_err(&kaweth->intf->dev,
+ "%s RX status: %d count: %d packet_len: %d\n",
+ net->name, status, count, (int)pkt_len);
kaweth_resubmit_rx_urb(kaweth, GFP_ATOMIC);
return;
}
if(kaweth->net && (count > 2)) {
if(pkt_len > (count - 2)) {
- err("Packet length too long for USB frame (pkt_len: %x, count: %x)",pkt_len, count);
- err("Packet len & 2047: %x", pkt_len & 2047);
- err("Count 2: %x", count2);
+ dev_err(&kaweth->intf->dev,
+ "Packet length too long for USB frame (pkt_len: %x, count: %x)\n",
+ pkt_len, count);
+ dev_err(&kaweth->intf->dev, "Packet len & 2047: %x\n",
+ pkt_len & 2047);
+ dev_err(&kaweth->intf->dev, "Count 2: %x\n", count2);
kaweth_resubmit_rx_urb(kaweth, GFP_ATOMIC);
return;
}
@@ -686,7 +691,7 @@ static int kaweth_open(struct net_device *net)
res = usb_autopm_get_interface(kaweth->intf);
if (res) {
- err("Interface cannot be resumed.");
+ dev_err(&kaweth->intf->dev, "Interface cannot be resumed.\n");
return -EIO;
}
res = kaweth_resubmit_rx_urb(kaweth, GFP_KERNEL);
@@ -907,7 +912,8 @@ static void kaweth_async_set_rx_mode(struct kaweth_device *kaweth)
KAWETH_CONTROL_TIMEOUT);
if(result < 0) {
- err("Failed to set Rx mode: %d", result);
+ dev_err(&kaweth->intf->dev, "Failed to set Rx mode: %d\n",
+ result);
}
else {
dbg("Set Rx mode to %d", packet_filter_bitmap);
@@ -1045,7 +1051,8 @@ static int kaweth_probe(
"kaweth/new_code.bin",
100,
2)) < 0) {
- err("Error downloading firmware (%d)", result);
+ dev_err(&intf->dev, "Error downloading firmware (%d)\n",
+ result);
goto err_fw;
}
@@ -1053,7 +1060,9 @@ static int kaweth_probe(
"kaweth/new_code_fix.bin",
100,
3)) < 0) {
- err("Error downloading firmware fix (%d)", result);
+ dev_err(&intf->dev,
+ "Error downloading firmware fix (%d)\n",
+ result);
goto err_fw;
}
@@ -1061,7 +1070,9 @@ static int kaweth_probe(
"kaweth/trigger_code.bin",
126,
2)) < 0) {
- err("Error downloading trigger code (%d)", result);
+ dev_err(&intf->dev,
+ "Error downloading trigger code (%d)\n",
+ result);
goto err_fw;
}
@@ -1070,13 +1081,14 @@ static int kaweth_probe(
"kaweth/trigger_code_fix.bin",
126,
3)) < 0) {
- err("Error downloading trigger code fix (%d)", result);
+ dev_err(&intf->dev, "Error downloading trigger code fix (%d)\n", result);
goto err_fw;
}
if ((result = kaweth_trigger_firmware(kaweth, 126)) < 0) {
- err("Error triggering firmware (%d)", result);
+ dev_err(&intf->dev, "Error triggering firmware (%d)\n",
+ result);
goto err_fw;
}
@@ -1091,7 +1103,7 @@ err_fw:
result = kaweth_read_configuration(kaweth);
if(result < 0) {
- err("Error reading configuration (%d), no net device created", result);
+ dev_err(&intf->dev, "Error reading configuration (%d), no net device created\n", result);
goto err_free_netdev;
}
@@ -1103,7 +1115,7 @@ err_fw:
if(!memcmp(&kaweth->configuration.hw_addr,
&bcast_addr,
sizeof(bcast_addr))) {
- err("Firmware not functioning properly, no net device created");
+ dev_err(&intf->dev, "Firmware not functioning properly, no net device created\n");
goto err_free_netdev;
}
@@ -1113,7 +1125,7 @@ err_fw:
}
if(kaweth_set_sofs_wait(kaweth, KAWETH_SOFS_TO_WAIT) < 0) {
- err("Error setting SOFS wait");
+ dev_err(&intf->dev, "Error setting SOFS wait\n");
goto err_free_netdev;
}
@@ -1123,7 +1135,7 @@ err_fw:
KAWETH_PACKET_FILTER_MULTICAST);
if(result < 0) {
- err("Error setting receive filter");
+ dev_err(&intf->dev, "Error setting receive filter\n");
goto err_free_netdev;
}
@@ -1175,7 +1187,7 @@ err_fw:
SET_NETDEV_DEV(netdev, &intf->dev);
if (register_netdev(netdev) != 0) {
- err("Error registering netdev.");
+ dev_err(&intf->dev, "Error registering netdev.\n");
goto err_intfdata;
}
diff --git a/drivers/net/usb/lg-vl600.c b/drivers/net/usb/lg-vl600.c
index 45a981fde43f..808d6506da41 100644
--- a/drivers/net/usb/lg-vl600.c
+++ b/drivers/net/usb/lg-vl600.c
@@ -344,6 +344,7 @@ static struct usb_driver lg_vl600_driver = {
.disconnect = usbnet_disconnect,
.suspend = usbnet_suspend,
.resume = usbnet_resume,
+ .disable_hub_initiated_lpm = 1,
};
module_usb_driver(lg_vl600_driver);
diff --git a/drivers/net/usb/mcs7830.c b/drivers/net/usb/mcs7830.c
index c434b6ba0337..add1064f755d 100644
--- a/drivers/net/usb/mcs7830.c
+++ b/drivers/net/usb/mcs7830.c
@@ -690,6 +690,7 @@ static struct usb_driver mcs7830_driver = {
.suspend = usbnet_suspend,
.resume = usbnet_resume,
.reset_resume = mcs7830_reset_resume,
+ .disable_hub_initiated_lpm = 1,
};
module_usb_driver(mcs7830_driver);
diff --git a/drivers/net/usb/net1080.c b/drivers/net/usb/net1080.c
index 83f965cb69e7..28c4d513ba85 100644
--- a/drivers/net/usb/net1080.c
+++ b/drivers/net/usb/net1080.c
@@ -587,6 +587,7 @@ static struct usb_driver net1080_driver = {
.disconnect = usbnet_disconnect,
.suspend = usbnet_suspend,
.resume = usbnet_resume,
+ .disable_hub_initiated_lpm = 1,
};
module_usb_driver(net1080_driver);
diff --git a/drivers/net/usb/pegasus.c b/drivers/net/usb/pegasus.c
index 752393092325..7023220456c5 100644
--- a/drivers/net/usb/pegasus.c
+++ b/drivers/net/usb/pegasus.c
@@ -1489,6 +1489,7 @@ static struct usb_driver pegasus_driver = {
.id_table = pegasus_ids,
.suspend = pegasus_suspend,
.resume = pegasus_resume,
+ .disable_hub_initiated_lpm = 1,
};
static void __init parse_id(char *id)
diff --git a/drivers/net/usb/plusb.c b/drivers/net/usb/plusb.c
index b2b035e29978..4584b9a805b3 100644
--- a/drivers/net/usb/plusb.c
+++ b/drivers/net/usb/plusb.c
@@ -152,6 +152,7 @@ static struct usb_driver plusb_driver = {
.disconnect = usbnet_disconnect,
.suspend = usbnet_suspend,
.resume = usbnet_resume,
+ .disable_hub_initiated_lpm = 1,
};
module_usb_driver(plusb_driver);
diff --git a/drivers/net/usb/qmi_wwan.c b/drivers/net/usb/qmi_wwan.c
index 63cfd0b2c31a..380dbea6109d 100644
--- a/drivers/net/usb/qmi_wwan.c
+++ b/drivers/net/usb/qmi_wwan.c
@@ -560,6 +560,7 @@ static struct usb_driver qmi_wwan_driver = {
.resume = qmi_wwan_resume,
.reset_resume = qmi_wwan_resume,
.supports_autosuspend = 1,
+ .disable_hub_initiated_lpm = 1,
};
static int __init qmi_wwan_init(void)
diff --git a/drivers/net/usb/rndis_host.c b/drivers/net/usb/rndis_host.c
index 0d746b3fdef1..4a4335833c36 100644
--- a/drivers/net/usb/rndis_host.c
+++ b/drivers/net/usb/rndis_host.c
@@ -638,6 +638,7 @@ static struct usb_driver rndis_driver = {
.disconnect = usbnet_disconnect,
.suspend = usbnet_suspend,
.resume = usbnet_resume,
+ .disable_hub_initiated_lpm = 1,
};
module_usb_driver(rndis_driver);
diff --git a/drivers/net/usb/rtl8150.c b/drivers/net/usb/rtl8150.c
index d363b31053da..0e2c92e0e532 100644
--- a/drivers/net/usb/rtl8150.c
+++ b/drivers/net/usb/rtl8150.c
@@ -203,7 +203,8 @@ static int async_set_registers(rtl8150_t * dev, u16 indx, u16 size)
if ((ret = usb_submit_urb(dev->ctrl_urb, GFP_ATOMIC))) {
if (ret == -ENODEV)
netif_device_detach(dev->netdev);
- err("control request submission failed: %d", ret);
+ dev_err(&dev->udev->dev,
+ "control request submission failed: %d\n", ret);
} else
set_bit(RX_REG_SET, &dev->flags);
@@ -516,9 +517,9 @@ resubmit:
if (res == -ENODEV)
netif_device_detach(dev->netdev);
else if (res)
- err ("can't resubmit intr, %s-%s/input0, status %d",
- dev->udev->bus->bus_name,
- dev->udev->devpath, res);
+ dev_err(&dev->udev->dev,
+ "can't resubmit intr, %s-%s/input0, status %d\n",
+ dev->udev->bus->bus_name, dev->udev->devpath, res);
}
static int rtl8150_suspend(struct usb_interface *intf, pm_message_t message)
@@ -890,11 +891,11 @@ static int rtl8150_probe(struct usb_interface *intf,
dev->intr_interval = 100; /* 100ms */
if (!alloc_all_urbs(dev)) {
- err("out of memory");
+ dev_err(&intf->dev, "out of memory\n");
goto out;
}
if (!rtl8150_reset(dev)) {
- err("couldn't reset the device");
+ dev_err(&intf->dev, "couldn't reset the device\n");
goto out1;
}
fill_skb_pool(dev);
@@ -903,7 +904,7 @@ static int rtl8150_probe(struct usb_interface *intf,
usb_set_intfdata(intf, dev);
SET_NETDEV_DEV(netdev, &intf->dev);
if (register_netdev(netdev) != 0) {
- err("couldn't register the device");
+ dev_err(&intf->dev, "couldn't register the device\n");
goto out2;
}
@@ -947,7 +948,8 @@ static struct usb_driver rtl8150_driver = {
.disconnect = rtl8150_disconnect,
.id_table = rtl8150_table,
.suspend = rtl8150_suspend,
- .resume = rtl8150_resume
+ .resume = rtl8150_resume,
+ .disable_hub_initiated_lpm = 1,
};
module_usb_driver(rtl8150_driver);
diff --git a/drivers/net/usb/sierra_net.c b/drivers/net/usb/sierra_net.c
index b59cf20c7817..3faef5670d1f 100644
--- a/drivers/net/usb/sierra_net.c
+++ b/drivers/net/usb/sierra_net.c
@@ -982,6 +982,7 @@ static struct usb_driver sierra_net_driver = {
.suspend = usbnet_suspend,
.resume = usbnet_resume,
.no_dynamic_id = 1,
+ .disable_hub_initiated_lpm = 1,
};
module_usb_driver(sierra_net_driver);
diff --git a/drivers/net/usb/smsc75xx.c b/drivers/net/usb/smsc75xx.c
index fb1a087b101d..1c6e51588da7 100644
--- a/drivers/net/usb/smsc75xx.c
+++ b/drivers/net/usb/smsc75xx.c
@@ -1254,6 +1254,7 @@ static struct usb_driver smsc75xx_driver = {
.suspend = usbnet_suspend,
.resume = usbnet_resume,
.disconnect = usbnet_disconnect,
+ .disable_hub_initiated_lpm = 1,
};
module_usb_driver(smsc75xx_driver);
diff --git a/drivers/net/usb/smsc95xx.c b/drivers/net/usb/smsc95xx.c
index 94ae66999f59..b1112e753859 100644
--- a/drivers/net/usb/smsc95xx.c
+++ b/drivers/net/usb/smsc95xx.c
@@ -1297,6 +1297,7 @@ static struct usb_driver smsc95xx_driver = {
.suspend = usbnet_suspend,
.resume = usbnet_resume,
.disconnect = usbnet_disconnect,
+ .disable_hub_initiated_lpm = 1,
};
module_usb_driver(smsc95xx_driver);
diff --git a/drivers/net/usb/zaurus.c b/drivers/net/usb/zaurus.c
index 34db195fb8b0..35c90307d473 100644
--- a/drivers/net/usb/zaurus.c
+++ b/drivers/net/usb/zaurus.c
@@ -377,6 +377,7 @@ static struct usb_driver zaurus_driver = {
.disconnect = usbnet_disconnect,
.suspend = usbnet_suspend,
.resume = usbnet_resume,
+ .disable_hub_initiated_lpm = 1,
};
module_usb_driver(zaurus_driver);
diff --git a/drivers/net/wan/Kconfig b/drivers/net/wan/Kconfig
index d70ede7a7f96..d58431e99f73 100644
--- a/drivers/net/wan/Kconfig
+++ b/drivers/net/wan/Kconfig
@@ -203,37 +203,6 @@ config WANXL_BUILD_FIRMWARE
You should never need this option, say N.
-config PC300
- tristate "Cyclades-PC300 support (RS-232/V.35, X.21, T1/E1 boards)"
- depends on HDLC && PCI && BROKEN
- ---help---
- This driver is broken because of struct tty_driver change.
-
- Driver for the Cyclades-PC300 synchronous communication boards.
-
- These boards provide synchronous serial interfaces to your
- Linux box (interfaces currently available are RS-232/V.35, X.21 and
- T1/E1). If you wish to support Multilink PPP, please select the
- option later and read the file README.mlppp provided by PC300
- package.
-
- To compile this as a module, choose M here: the module
- will be called pc300.
-
- If unsure, say N.
-
-config PC300_MLPPP
- bool "Cyclades-PC300 MLPPP support"
- depends on PC300 && PPP_MULTILINK && PPP_SYNC_TTY && HDLC_PPP
- help
- Multilink PPP over the PC300 synchronous communication boards.
-
-comment "Cyclades-PC300 MLPPP support is disabled."
- depends on HDLC && PC300 && (PPP=n || !PPP_MULTILINK || PPP_SYNC_TTY=n || !HDLC_PPP)
-
-comment "Refer to the file README.mlppp, provided by PC300 package."
- depends on HDLC && PC300 && (PPP=n || !PPP_MULTILINK || PPP_SYNC_TTY=n || !HDLC_PPP)
-
config PC300TOO
tristate "Cyclades PC300 RSV/X21 alternative support"
depends on HDLC && PCI
diff --git a/drivers/net/wan/Makefile b/drivers/net/wan/Makefile
index 19d14bc28356..eac709bed7ae 100644
--- a/drivers/net/wan/Makefile
+++ b/drivers/net/wan/Makefile
@@ -17,10 +17,6 @@ obj-$(CONFIG_HDLC_FR) += hdlc_fr.o
obj-$(CONFIG_HDLC_PPP) += hdlc_ppp.o
obj-$(CONFIG_HDLC_X25) += hdlc_x25.o
-pc300-y := pc300_drv.o
-pc300-$(CONFIG_PC300_MLPPP) += pc300_tty.o
-pc300-objs := $(pc300-y)
-
obj-$(CONFIG_HOSTESS_SV11) += z85230.o hostess_sv11.o
obj-$(CONFIG_SEALEVEL_4021) += z85230.o sealevel.o
obj-$(CONFIG_COSA) += cosa.o
@@ -35,7 +31,6 @@ obj-$(CONFIG_SDLA) += sdla.o
obj-$(CONFIG_CYCLADES_SYNC) += cycx_drv.o cyclomx.o
obj-$(CONFIG_LAPBETHER) += lapbether.o
obj-$(CONFIG_SBNI) += sbni.o
-obj-$(CONFIG_PC300) += pc300.o
obj-$(CONFIG_N2) += n2.o
obj-$(CONFIG_C101) += c101.o
obj-$(CONFIG_WANXL) += wanxl.o
diff --git a/drivers/net/wan/pc300-falc-lh.h b/drivers/net/wan/pc300-falc-lh.h
deleted file mode 100644
index 01ed23ca76c7..000000000000
--- a/drivers/net/wan/pc300-falc-lh.h
+++ /dev/null
@@ -1,1238 +0,0 @@
-/*
- * falc.h Description of the Siemens FALC T1/E1 framer.
- *
- * Author: Ivan Passos <ivan@cyclades.com>
- *
- * Copyright: (c) 2000-2001 Cyclades Corp.
- *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License
- * as published by the Free Software Foundation; either version
- * 2 of the License, or (at your option) any later version.
- *
- * $Log: falc-lh.h,v $
- * Revision 3.1 2001/06/15 12:41:10 regina
- * upping major version number
- *
- * Revision 1.1.1.1 2001/06/13 20:24:47 daniela
- * PC300 initial CVS version (3.4.0-pre1)
- *
- * Revision 1.1 2000/05/15 ivan
- * Included DJA bits for the LIM2 register.
- *
- * Revision 1.0 2000/02/22 ivan
- * Initial version.
- *
- */
-
-#ifndef _FALC_LH_H
-#define _FALC_LH_H
-
-#define NUM_OF_T1_CHANNELS 24
-#define NUM_OF_E1_CHANNELS 32
-
-/*>>>>>>>>>>>>>>>>> FALC Register Bits (Transmit Mode) <<<<<<<<<<<<<<<<<<< */
-
-/* CMDR (Command Register)
- ---------------- E1 & T1 ------------------------------ */
-#define CMDR_RMC 0x80
-#define CMDR_RRES 0x40
-#define CMDR_XREP 0x20
-#define CMDR_XRES 0x10
-#define CMDR_XHF 0x08
-#define CMDR_XTF 0x04
-#define CMDR_XME 0x02
-#define CMDR_SRES 0x01
-
-/* MODE (Mode Register)
- ----------------- E1 & T1 ----------------------------- */
-#define MODE_MDS2 0x80
-#define MODE_MDS1 0x40
-#define MODE_MDS0 0x20
-#define MODE_BRAC 0x10
-#define MODE_HRAC 0x08
-
-/* IPC (Interrupt Port Configuration)
- ----------------- E1 & T1 ----------------------------- */
-#define IPC_VIS 0x80
-#define IPC_SCI 0x04
-#define IPC_IC1 0x02
-#define IPC_IC0 0x01
-
-/* CCR1 (Common Configuration Register 1)
- ----------------- E1 & T1 ----------------------------- */
-#define CCR1_SFLG 0x80
-#define CCR1_XTS16RA 0x40
-#define CCR1_BRM 0x40
-#define CCR1_CASSYM 0x20
-#define CCR1_EDLX 0x20
-#define CCR1_EITS 0x10
-#define CCR1_ITF 0x08
-#define CCR1_RFT1 0x02
-#define CCR1_RFT0 0x01
-
-/* CCR3 (Common Configuration Register 3)
- ---------------- E1 & T1 ------------------------------ */
-
-#define CCR3_PRE1 0x80
-#define CCR3_PRE0 0x40
-#define CCR3_EPT 0x20
-#define CCR3_RADD 0x10
-#define CCR3_RCRC 0x04
-#define CCR3_XCRC 0x02
-
-
-/* RTR1-4 (Receive Timeslot Register 1-4)
- ---------------- E1 & T1 ------------------------------ */
-
-#define RTR1_TS0 0x80
-#define RTR1_TS1 0x40
-#define RTR1_TS2 0x20
-#define RTR1_TS3 0x10
-#define RTR1_TS4 0x08
-#define RTR1_TS5 0x04
-#define RTR1_TS6 0x02
-#define RTR1_TS7 0x01
-
-#define RTR2_TS8 0x80
-#define RTR2_TS9 0x40
-#define RTR2_TS10 0x20
-#define RTR2_TS11 0x10
-#define RTR2_TS12 0x08
-#define RTR2_TS13 0x04
-#define RTR2_TS14 0x02
-#define RTR2_TS15 0x01
-
-#define RTR3_TS16 0x80
-#define RTR3_TS17 0x40
-#define RTR3_TS18 0x20
-#define RTR3_TS19 0x10
-#define RTR3_TS20 0x08
-#define RTR3_TS21 0x04
-#define RTR3_TS22 0x02
-#define RTR3_TS23 0x01
-
-#define RTR4_TS24 0x80
-#define RTR4_TS25 0x40
-#define RTR4_TS26 0x20
-#define RTR4_TS27 0x10
-#define RTR4_TS28 0x08
-#define RTR4_TS29 0x04
-#define RTR4_TS30 0x02
-#define RTR4_TS31 0x01
-
-
-/* TTR1-4 (Transmit Timeslot Register 1-4)
- ---------------- E1 & T1 ------------------------------ */
-
-#define TTR1_TS0 0x80
-#define TTR1_TS1 0x40
-#define TTR1_TS2 0x20
-#define TTR1_TS3 0x10
-#define TTR1_TS4 0x08
-#define TTR1_TS5 0x04
-#define TTR1_TS6 0x02
-#define TTR1_TS7 0x01
-
-#define TTR2_TS8 0x80
-#define TTR2_TS9 0x40
-#define TTR2_TS10 0x20
-#define TTR2_TS11 0x10
-#define TTR2_TS12 0x08
-#define TTR2_TS13 0x04
-#define TTR2_TS14 0x02
-#define TTR2_TS15 0x01
-
-#define TTR3_TS16 0x80
-#define TTR3_TS17 0x40
-#define TTR3_TS18 0x20
-#define TTR3_TS19 0x10
-#define TTR3_TS20 0x08
-#define TTR3_TS21 0x04
-#define TTR3_TS22 0x02
-#define TTR3_TS23 0x01
-
-#define TTR4_TS24 0x80
-#define TTR4_TS25 0x40
-#define TTR4_TS26 0x20
-#define TTR4_TS27 0x10
-#define TTR4_TS28 0x08
-#define TTR4_TS29 0x04
-#define TTR4_TS30 0x02
-#define TTR4_TS31 0x01
-
-
-
-/* IMR0-4 (Interrupt Mask Register 0-4)
-
- ----------------- E1 & T1 ----------------------------- */
-
-#define IMR0_RME 0x80
-#define IMR0_RFS 0x40
-#define IMR0_T8MS 0x20
-#define IMR0_ISF 0x20
-#define IMR0_RMB 0x10
-#define IMR0_CASC 0x08
-#define IMR0_RSC 0x08
-#define IMR0_CRC6 0x04
-#define IMR0_CRC4 0x04
-#define IMR0_PDEN 0x02
-#define IMR0_RPF 0x01
-
-#define IMR1_CASE 0x80
-#define IMR1_RDO 0x40
-#define IMR1_ALLS 0x20
-#define IMR1_XDU 0x10
-#define IMR1_XMB 0x08
-#define IMR1_XLSC 0x02
-#define IMR1_XPR 0x01
-#define IMR1_LLBSC 0x80
-
-#define IMR2_FAR 0x80
-#define IMR2_LFA 0x40
-#define IMR2_MFAR 0x20
-#define IMR2_T400MS 0x10
-#define IMR2_LMFA 0x10
-#define IMR2_AIS 0x08
-#define IMR2_LOS 0x04
-#define IMR2_RAR 0x02
-#define IMR2_RA 0x01
-
-#define IMR3_ES 0x80
-#define IMR3_SEC 0x40
-#define IMR3_LMFA16 0x20
-#define IMR3_AIS16 0x10
-#define IMR3_RA16 0x08
-#define IMR3_API 0x04
-#define IMR3_XSLP 0x20
-#define IMR3_XSLN 0x10
-#define IMR3_LLBSC 0x08
-#define IMR3_XRS 0x04
-#define IMR3_SLN 0x02
-#define IMR3_SLP 0x01
-
-#define IMR4_LFA 0x80
-#define IMR4_FER 0x40
-#define IMR4_CER 0x20
-#define IMR4_AIS 0x10
-#define IMR4_LOS 0x08
-#define IMR4_CVE 0x04
-#define IMR4_SLIP 0x02
-#define IMR4_EBE 0x01
-
-/* FMR0-5 for E1 and T1 (Framer Mode Register ) */
-
-#define FMR0_XC1 0x80
-#define FMR0_XC0 0x40
-#define FMR0_RC1 0x20
-#define FMR0_RC0 0x10
-#define FMR0_EXTD 0x08
-#define FMR0_ALM 0x04
-#define E1_FMR0_FRS 0x02
-#define T1_FMR0_FRS 0x08
-#define FMR0_SRAF 0x04
-#define FMR0_EXLS 0x02
-#define FMR0_SIM 0x01
-
-#define FMR1_MFCS 0x80
-#define FMR1_AFR 0x40
-#define FMR1_ENSA 0x20
-#define FMR1_CTM 0x80
-#define FMR1_SIGM 0x40
-#define FMR1_EDL 0x20
-#define FMR1_PMOD 0x10
-#define FMR1_XFS 0x08
-#define FMR1_CRC 0x08
-#define FMR1_ECM 0x04
-#define FMR1_IMOD 0x02
-#define FMR1_XAIS 0x01
-
-#define FMR2_RFS1 0x80
-#define FMR2_RFS0 0x40
-#define FMR2_MCSP 0x40
-#define FMR2_RTM 0x20
-#define FMR2_SSP 0x20
-#define FMR2_DAIS 0x10
-#define FMR2_SAIS 0x08
-#define FMR2_PLB 0x04
-#define FMR2_AXRA 0x02
-#define FMR2_ALMF 0x01
-#define FMR2_EXZE 0x01
-
-#define LOOP_RTM 0x40
-#define LOOP_SFM 0x40
-#define LOOP_ECLB 0x20
-#define LOOP_CLA 0x1f
-
-/*--------------------- E1 ----------------------------*/
-#define FMR3_XLD 0x20
-#define FMR3_XLU 0x10
-
-/*--------------------- T1 ----------------------------*/
-#define FMR4_AIS3 0x80
-#define FMR4_TM 0x40
-#define FMR4_XRA 0x20
-#define FMR4_SSC1 0x10
-#define FMR4_SSC0 0x08
-#define FMR4_AUTO 0x04
-#define FMR4_FM1 0x02
-#define FMR4_FM0 0x01
-
-#define FMR5_SRS 0x80
-#define FMR5_EIBR 0x40
-#define FMR5_XLD 0x20
-#define FMR5_XLU 0x10
-
-
-/* LOOP (Channel Loop Back)
-
- ------------------ E1 & T1 ---------------------------- */
-
-#define LOOP_SFM 0x40
-#define LOOP_ECLB 0x20
-#define LOOP_CLA4 0x10
-#define LOOP_CLA3 0x08
-#define LOOP_CLA2 0x04
-#define LOOP_CLA1 0x02
-#define LOOP_CLA0 0x01
-
-
-
-/* XSW (Transmit Service Word Pulseframe)
-
- ------------------- E1 --------------------------- */
-
-#define XSW_XSIS 0x80
-#define XSW_XTM 0x40
-#define XSW_XRA 0x20
-#define XSW_XY0 0x10
-#define XSW_XY1 0x08
-#define XSW_XY2 0x04
-#define XSW_XY3 0x02
-#define XSW_XY4 0x01
-
-
-/* XSP (Transmit Spare Bits)
-
- ------------------- E1 --------------------------- */
-
-#define XSP_XAP 0x80
-#define XSP_CASEN 0x40
-#define XSP_TT0 0x20
-#define XSP_EBP 0x10
-#define XSP_AXS 0x08
-#define XSP_XSIF 0x04
-#define XSP_XS13 0x02
-#define XSP_XS15 0x01
-
-
-/* XC0/1 (Transmit Control 0/1)
- ------------------ E1 & T1 ---------------------------- */
-
-#define XC0_SA8E 0x80
-#define XC0_SA7E 0x40
-#define XC0_SA6E 0x20
-#define XC0_SA5E 0x10
-#define XC0_SA4E 0x08
-#define XC0_BRM 0x80
-#define XC0_MFBS 0x40
-#define XC0_SFRZ 0x10
-#define XC0_XCO2 0x04
-#define XC0_XCO1 0x02
-#define XC0_XCO0 0x01
-
-#define XC1_XTO5 0x20
-#define XC1_XTO4 0x10
-#define XC1_XTO3 0x08
-#define XC1_XTO2 0x04
-#define XC1_XTO1 0x02
-#define XC1_XTO0 0x01
-
-
-/* RC0/1 (Receive Control 0/1)
- ------------------ E1 & T1 ---------------------------- */
-
-#define RC0_SICS 0x40
-#define RC0_CRCI 0x20
-#define RC0_XCRCI 0x10
-#define RC0_RDIS 0x08
-#define RC0_RCO2 0x04
-#define RC0_RCO1 0x02
-#define RC0_RCO0 0x01
-
-#define RC1_SWD 0x80
-#define RC1_ASY4 0x40
-#define RC1_RRAM 0x40
-#define RC1_RTO5 0x20
-#define RC1_RTO4 0x10
-#define RC1_RTO3 0x08
-#define RC1_RTO2 0x04
-#define RC1_RTO1 0x02
-#define RC1_RTO0 0x01
-
-
-
-/* XPM0-2 (Transmit Pulse Mask 0-2)
- --------------------- E1 & T1 ------------------------- */
-
-#define XPM0_XP12 0x80
-#define XPM0_XP11 0x40
-#define XPM0_XP10 0x20
-#define XPM0_XP04 0x10
-#define XPM0_XP03 0x08
-#define XPM0_XP02 0x04
-#define XPM0_XP01 0x02
-#define XPM0_XP00 0x01
-
-#define XPM1_XP30 0x80
-#define XPM1_XP24 0x40
-#define XPM1_XP23 0x20
-#define XPM1_XP22 0x10
-#define XPM1_XP21 0x08
-#define XPM1_XP20 0x04
-#define XPM1_XP14 0x02
-#define XPM1_XP13 0x01
-
-#define XPM2_XLHP 0x80
-#define XPM2_XLT 0x40
-#define XPM2_DAXLT 0x20
-#define XPM2_XP34 0x08
-#define XPM2_XP33 0x04
-#define XPM2_XP32 0x02
-#define XPM2_XP31 0x01
-
-
-/* TSWM (Transparent Service Word Mask)
- ------------------ E1 ---------------------------- */
-
-#define TSWM_TSIS 0x80
-#define TSWM_TSIF 0x40
-#define TSWM_TRA 0x20
-#define TSWM_TSA4 0x10
-#define TSWM_TSA5 0x08
-#define TSWM_TSA6 0x04
-#define TSWM_TSA7 0x02
-#define TSWM_TSA8 0x01
-
-/* IDLE <Idle Channel Code Register>
-
- ------------------ E1 & T1 ----------------------- */
-
-#define IDLE_IDL7 0x80
-#define IDLE_IDL6 0x40
-#define IDLE_IDL5 0x20
-#define IDLE_IDL4 0x10
-#define IDLE_IDL3 0x08
-#define IDLE_IDL2 0x04
-#define IDLE_IDL1 0x02
-#define IDLE_IDL0 0x01
-
-
-/* XSA4-8 <Transmit SA4-8 Register(Read/Write) >
- -------------------E1 ----------------------------- */
-
-#define XSA4_XS47 0x80
-#define XSA4_XS46 0x40
-#define XSA4_XS45 0x20
-#define XSA4_XS44 0x10
-#define XSA4_XS43 0x08
-#define XSA4_XS42 0x04
-#define XSA4_XS41 0x02
-#define XSA4_XS40 0x01
-
-#define XSA5_XS57 0x80
-#define XSA5_XS56 0x40
-#define XSA5_XS55 0x20
-#define XSA5_XS54 0x10
-#define XSA5_XS53 0x08
-#define XSA5_XS52 0x04
-#define XSA5_XS51 0x02
-#define XSA5_XS50 0x01
-
-#define XSA6_XS67 0x80
-#define XSA6_XS66 0x40
-#define XSA6_XS65 0x20
-#define XSA6_XS64 0x10
-#define XSA6_XS63 0x08
-#define XSA6_XS62 0x04
-#define XSA6_XS61 0x02
-#define XSA6_XS60 0x01
-
-#define XSA7_XS77 0x80
-#define XSA7_XS76 0x40
-#define XSA7_XS75 0x20
-#define XSA7_XS74 0x10
-#define XSA7_XS73 0x08
-#define XSA7_XS72 0x04
-#define XSA7_XS71 0x02
-#define XSA7_XS70 0x01
-
-#define XSA8_XS87 0x80
-#define XSA8_XS86 0x40
-#define XSA8_XS85 0x20
-#define XSA8_XS84 0x10
-#define XSA8_XS83 0x08
-#define XSA8_XS82 0x04
-#define XSA8_XS81 0x02
-#define XSA8_XS80 0x01
-
-
-/* XDL1-3 (Transmit DL-Bit Register1-3 (read/write))
- ----------------------- T1 --------------------- */
-
-#define XDL1_XDL17 0x80
-#define XDL1_XDL16 0x40
-#define XDL1_XDL15 0x20
-#define XDL1_XDL14 0x10
-#define XDL1_XDL13 0x08
-#define XDL1_XDL12 0x04
-#define XDL1_XDL11 0x02
-#define XDL1_XDL10 0x01
-
-#define XDL2_XDL27 0x80
-#define XDL2_XDL26 0x40
-#define XDL2_XDL25 0x20
-#define XDL2_XDL24 0x10
-#define XDL2_XDL23 0x08
-#define XDL2_XDL22 0x04
-#define XDL2_XDL21 0x02
-#define XDL2_XDL20 0x01
-
-#define XDL3_XDL37 0x80
-#define XDL3_XDL36 0x40
-#define XDL3_XDL35 0x20
-#define XDL3_XDL34 0x10
-#define XDL3_XDL33 0x08
-#define XDL3_XDL32 0x04
-#define XDL3_XDL31 0x02
-#define XDL3_XDL30 0x01
-
-
-/* ICB1-4 (Idle Channel Register 1-4)
- ------------------ E1 ---------------------------- */
-
-#define E1_ICB1_IC0 0x80
-#define E1_ICB1_IC1 0x40
-#define E1_ICB1_IC2 0x20
-#define E1_ICB1_IC3 0x10
-#define E1_ICB1_IC4 0x08
-#define E1_ICB1_IC5 0x04
-#define E1_ICB1_IC6 0x02
-#define E1_ICB1_IC7 0x01
-
-#define E1_ICB2_IC8 0x80
-#define E1_ICB2_IC9 0x40
-#define E1_ICB2_IC10 0x20
-#define E1_ICB2_IC11 0x10
-#define E1_ICB2_IC12 0x08
-#define E1_ICB2_IC13 0x04
-#define E1_ICB2_IC14 0x02
-#define E1_ICB2_IC15 0x01
-
-#define E1_ICB3_IC16 0x80
-#define E1_ICB3_IC17 0x40
-#define E1_ICB3_IC18 0x20
-#define E1_ICB3_IC19 0x10
-#define E1_ICB3_IC20 0x08
-#define E1_ICB3_IC21 0x04
-#define E1_ICB3_IC22 0x02
-#define E1_ICB3_IC23 0x01
-
-#define E1_ICB4_IC24 0x80
-#define E1_ICB4_IC25 0x40
-#define E1_ICB4_IC26 0x20
-#define E1_ICB4_IC27 0x10
-#define E1_ICB4_IC28 0x08
-#define E1_ICB4_IC29 0x04
-#define E1_ICB4_IC30 0x02
-#define E1_ICB4_IC31 0x01
-
-/* ICB1-4 (Idle Channel Register 1-4)
- ------------------ T1 ---------------------------- */
-
-#define T1_ICB1_IC1 0x80
-#define T1_ICB1_IC2 0x40
-#define T1_ICB1_IC3 0x20
-#define T1_ICB1_IC4 0x10
-#define T1_ICB1_IC5 0x08
-#define T1_ICB1_IC6 0x04
-#define T1_ICB1_IC7 0x02
-#define T1_ICB1_IC8 0x01
-
-#define T1_ICB2_IC9 0x80
-#define T1_ICB2_IC10 0x40
-#define T1_ICB2_IC11 0x20
-#define T1_ICB2_IC12 0x10
-#define T1_ICB2_IC13 0x08
-#define T1_ICB2_IC14 0x04
-#define T1_ICB2_IC15 0x02
-#define T1_ICB2_IC16 0x01
-
-#define T1_ICB3_IC17 0x80
-#define T1_ICB3_IC18 0x40
-#define T1_ICB3_IC19 0x20
-#define T1_ICB3_IC20 0x10
-#define T1_ICB3_IC21 0x08
-#define T1_ICB3_IC22 0x04
-#define T1_ICB3_IC23 0x02
-#define T1_ICB3_IC24 0x01
-
-/* FMR3 (Framer Mode Register 3)
- --------------------E1------------------------ */
-
-#define FMR3_CMI 0x08
-#define FMR3_SYNSA 0x04
-#define FMR3_CFRZ 0x02
-#define FMR3_EXTIW 0x01
-
-
-
-/* CCB1-3 (Clear Channel Register)
- ------------------- T1 ----------------------- */
-
-#define CCB1_CH1 0x80
-#define CCB1_CH2 0x40
-#define CCB1_CH3 0x20
-#define CCB1_CH4 0x10
-#define CCB1_CH5 0x08
-#define CCB1_CH6 0x04
-#define CCB1_CH7 0x02
-#define CCB1_CH8 0x01
-
-#define CCB2_CH9 0x80
-#define CCB2_CH10 0x40
-#define CCB2_CH11 0x20
-#define CCB2_CH12 0x10
-#define CCB2_CH13 0x08
-#define CCB2_CH14 0x04
-#define CCB2_CH15 0x02
-#define CCB2_CH16 0x01
-
-#define CCB3_CH17 0x80
-#define CCB3_CH18 0x40
-#define CCB3_CH19 0x20
-#define CCB3_CH20 0x10
-#define CCB3_CH21 0x08
-#define CCB3_CH22 0x04
-#define CCB3_CH23 0x02
-#define CCB3_CH24 0x01
-
-
-/* LIM0/1 (Line Interface Mode 0/1)
- ------------------- E1 & T1 --------------------------- */
-
-#define LIM0_XFB 0x80
-#define LIM0_XDOS 0x40
-#define LIM0_SCL1 0x20
-#define LIM0_SCL0 0x10
-#define LIM0_EQON 0x08
-#define LIM0_ELOS 0x04
-#define LIM0_LL 0x02
-#define LIM0_MAS 0x01
-
-#define LIM1_EFSC 0x80
-#define LIM1_RIL2 0x40
-#define LIM1_RIL1 0x20
-#define LIM1_RIL0 0x10
-#define LIM1_DCOC 0x08
-#define LIM1_JATT 0x04
-#define LIM1_RL 0x02
-#define LIM1_DRS 0x01
-
-
-/* PCDR (Pulse Count Detection Register(Read/Write))
- ------------------ E1 & T1 ------------------------- */
-
-#define PCDR_PCD7 0x80
-#define PCDR_PCD6 0x40
-#define PCDR_PCD5 0x20
-#define PCDR_PCD4 0x10
-#define PCDR_PCD3 0x08
-#define PCDR_PCD2 0x04
-#define PCDR_PCD1 0x02
-#define PCDR_PCD0 0x01
-
-#define PCRR_PCR7 0x80
-#define PCRR_PCR6 0x40
-#define PCRR_PCR5 0x20
-#define PCRR_PCR4 0x10
-#define PCRR_PCR3 0x08
-#define PCRR_PCR2 0x04
-#define PCRR_PCR1 0x02
-#define PCRR_PCR0 0x01
-
-
-/* LIM2 (Line Interface Mode 2)
-
- ------------------ E1 & T1 ---------------------------- */
-
-#define LIM2_DJA2 0x20
-#define LIM2_DJA1 0x10
-#define LIM2_LOS2 0x02
-#define LIM2_LOS1 0x01
-
-/* LCR1 (Loop Code Register 1) */
-
-#define LCR1_EPRM 0x80
-#define LCR1_XPRBS 0x40
-
-/* SIC1 (System Interface Control 1) */
-#define SIC1_SRSC 0x80
-#define SIC1_RBS1 0x20
-#define SIC1_RBS0 0x10
-#define SIC1_SXSC 0x08
-#define SIC1_XBS1 0x02
-#define SIC1_XBS0 0x01
-
-/* DEC (Disable Error Counter)
- ------------------ E1 & T1 ---------------------------- */
-
-#define DEC_DCEC3 0x20
-#define DEC_DBEC 0x10
-#define DEC_DCEC1 0x08
-#define DEC_DCEC 0x08
-#define DEC_DEBC 0x04
-#define DEC_DCVC 0x02
-#define DEC_DFEC 0x01
-
-
-/* FALC Register Bits (Receive Mode)
- ---------------------------------------------------------------------------- */
-
-
-/* FRS0/1 (Framer Receive Status Register 0/1)
- ----------------- E1 & T1 ---------------------------------- */
-
-#define FRS0_LOS 0x80
-#define FRS0_AIS 0x40
-#define FRS0_LFA 0x20
-#define FRS0_RRA 0x10
-#define FRS0_API 0x08
-#define FRS0_NMF 0x04
-#define FRS0_LMFA 0x02
-#define FRS0_FSRF 0x01
-
-#define FRS1_TS16RA 0x40
-#define FRS1_TS16LOS 0x20
-#define FRS1_TS16AIS 0x10
-#define FRS1_TS16LFA 0x08
-#define FRS1_EXZD 0x80
-#define FRS1_LLBDD 0x10
-#define FRS1_LLBAD 0x08
-#define FRS1_XLS 0x02
-#define FRS1_XLO 0x01
-#define FRS1_PDEN 0x40
-
-/* FRS2/3 (Framer Receive Status Register 2/3)
- ----------------- T1 ---------------------------------- */
-
-#define FRS2_ESC2 0x80
-#define FRS2_ESC1 0x40
-#define FRS2_ESC0 0x20
-
-#define FRS3_FEH5 0x20
-#define FRS3_FEH4 0x10
-#define FRS3_FEH3 0x08
-#define FRS3_FEH2 0x04
-#define FRS3_FEH1 0x02
-#define FRS3_FEH0 0x01
-
-
-/* RSW (Receive Service Word Pulseframe)
- ----------------- E1 ------------------------------ */
-
-#define RSW_RSI 0x80
-#define RSW_RRA 0x20
-#define RSW_RYO 0x10
-#define RSW_RY1 0x08
-#define RSW_RY2 0x04
-#define RSW_RY3 0x02
-#define RSW_RY4 0x01
-
-
-/* RSP (Receive Spare Bits / Additional Status)
- ---------------- E1 ------------------------------- */
-
-#define RSP_SI1 0x80
-#define RSP_SI2 0x40
-#define RSP_LLBDD 0x10
-#define RSP_LLBAD 0x08
-#define RSP_RSIF 0x04
-#define RSP_RS13 0x02
-#define RSP_RS15 0x01
-
-
-/* FECL (Framing Error Counter)
- ---------------- E1 & T1 -------------------------- */
-
-#define FECL_FE7 0x80
-#define FECL_FE6 0x40
-#define FECL_FE5 0x20
-#define FECL_FE4 0x10
-#define FECL_FE3 0x08
-#define FECL_FE2 0x04
-#define FECL_FE1 0x02
-#define FECL_FE0 0x01
-
-#define FECH_FE15 0x80
-#define FECH_FE14 0x40
-#define FECH_FE13 0x20
-#define FECH_FE12 0x10
-#define FECH_FE11 0x08
-#define FECH_FE10 0x04
-#define FECH_FE9 0x02
-#define FECH_FE8 0x01
-
-
-/* CVCl (Code Violation Counter)
- ----------------- E1 ------------------------- */
-
-#define CVCL_CV7 0x80
-#define CVCL_CV6 0x40
-#define CVCL_CV5 0x20
-#define CVCL_CV4 0x10
-#define CVCL_CV3 0x08
-#define CVCL_CV2 0x04
-#define CVCL_CV1 0x02
-#define CVCL_CV0 0x01
-
-#define CVCH_CV15 0x80
-#define CVCH_CV14 0x40
-#define CVCH_CV13 0x20
-#define CVCH_CV12 0x10
-#define CVCH_CV11 0x08
-#define CVCH_CV10 0x04
-#define CVCH_CV9 0x02
-#define CVCH_CV8 0x01
-
-
-/* CEC1-3L (CRC Error Counter)
- ------------------ E1 ----------------------------- */
-
-#define CEC1L_CR7 0x80
-#define CEC1L_CR6 0x40
-#define CEC1L_CR5 0x20
-#define CEC1L_CR4 0x10
-#define CEC1L_CR3 0x08
-#define CEC1L_CR2 0x04
-#define CEC1L_CR1 0x02
-#define CEC1L_CR0 0x01
-
-#define CEC1H_CR15 0x80
-#define CEC1H_CR14 0x40
-#define CEC1H_CR13 0x20
-#define CEC1H_CR12 0x10
-#define CEC1H_CR11 0x08
-#define CEC1H_CR10 0x04
-#define CEC1H_CR9 0x02
-#define CEC1H_CR8 0x01
-
-#define CEC2L_CR7 0x80
-#define CEC2L_CR6 0x40
-#define CEC2L_CR5 0x20
-#define CEC2L_CR4 0x10
-#define CEC2L_CR3 0x08
-#define CEC2L_CR2 0x04
-#define CEC2L_CR1 0x02
-#define CEC2L_CR0 0x01
-
-#define CEC2H_CR15 0x80
-#define CEC2H_CR14 0x40
-#define CEC2H_CR13 0x20
-#define CEC2H_CR12 0x10
-#define CEC2H_CR11 0x08
-#define CEC2H_CR10 0x04
-#define CEC2H_CR9 0x02
-#define CEC2H_CR8 0x01
-
-#define CEC3L_CR7 0x80
-#define CEC3L_CR6 0x40
-#define CEC3L_CR5 0x20
-#define CEC3L_CR4 0x10
-#define CEC3L_CR3 0x08
-#define CEC3L_CR2 0x04
-#define CEC3L_CR1 0x02
-#define CEC3L_CR0 0x01
-
-#define CEC3H_CR15 0x80
-#define CEC3H_CR14 0x40
-#define CEC3H_CR13 0x20
-#define CEC3H_CR12 0x10
-#define CEC3H_CR11 0x08
-#define CEC3H_CR10 0x04
-#define CEC3H_CR9 0x02
-#define CEC3H_CR8 0x01
-
-
-/* CECL (CRC Error Counter)
-
- ------------------ T1 ----------------------------- */
-
-#define CECL_CR7 0x80
-#define CECL_CR6 0x40
-#define CECL_CR5 0x20
-#define CECL_CR4 0x10
-#define CECL_CR3 0x08
-#define CECL_CR2 0x04
-#define CECL_CR1 0x02
-#define CECL_CR0 0x01
-
-#define CECH_CR15 0x80
-#define CECH_CR14 0x40
-#define CECH_CR13 0x20
-#define CECH_CR12 0x10
-#define CECH_CR11 0x08
-#define CECH_CR10 0x04
-#define CECH_CR9 0x02
-#define CECH_CR8 0x01
-
-/* EBCL (E Bit Error Counter)
- ------------------- E1 & T1 ------------------------- */
-
-#define EBCL_EB7 0x80
-#define EBCL_EB6 0x40
-#define EBCL_EB5 0x20
-#define EBCL_EB4 0x10
-#define EBCL_EB3 0x08
-#define EBCL_EB2 0x04
-#define EBCL_EB1 0x02
-#define EBCL_EB0 0x01
-
-#define EBCH_EB15 0x80
-#define EBCH_EB14 0x40
-#define EBCH_EB13 0x20
-#define EBCH_EB12 0x10
-#define EBCH_EB11 0x08
-#define EBCH_EB10 0x04
-#define EBCH_EB9 0x02
-#define EBCH_EB8 0x01
-
-
-/* RSA4-8 (Receive Sa4-8-Bit Register)
- -------------------- E1 --------------------------- */
-
-#define RSA4_RS47 0x80
-#define RSA4_RS46 0x40
-#define RSA4_RS45 0x20
-#define RSA4_RS44 0x10
-#define RSA4_RS43 0x08
-#define RSA4_RS42 0x04
-#define RSA4_RS41 0x02
-#define RSA4_RS40 0x01
-
-#define RSA5_RS57 0x80
-#define RSA5_RS56 0x40
-#define RSA5_RS55 0x20
-#define RSA5_RS54 0x10
-#define RSA5_RS53 0x08
-#define RSA5_RS52 0x04
-#define RSA5_RS51 0x02
-#define RSA5_RS50 0x01
-
-#define RSA6_RS67 0x80
-#define RSA6_RS66 0x40
-#define RSA6_RS65 0x20
-#define RSA6_RS64 0x10
-#define RSA6_RS63 0x08
-#define RSA6_RS62 0x04
-#define RSA6_RS61 0x02
-#define RSA6_RS60 0x01
-
-#define RSA7_RS77 0x80
-#define RSA7_RS76 0x40
-#define RSA7_RS75 0x20
-#define RSA7_RS74 0x10
-#define RSA7_RS73 0x08
-#define RSA7_RS72 0x04
-#define RSA7_RS71 0x02
-#define RSA7_RS70 0x01
-
-#define RSA8_RS87 0x80
-#define RSA8_RS86 0x40
-#define RSA8_RS85 0x20
-#define RSA8_RS84 0x10
-#define RSA8_RS83 0x08
-#define RSA8_RS82 0x04
-#define RSA8_RS81 0x02
-#define RSA8_RS80 0x01
-
-/* RSA6S (Receive Sa6 Bit Status Register)
- ------------------------ T1 ------------------------- */
-
-#define RSA6S_SX 0x20
-#define RSA6S_SF 0x10
-#define RSA6S_SE 0x08
-#define RSA6S_SC 0x04
-#define RSA6S_SA 0x02
-#define RSA6S_S8 0x01
-
-
-/* RDL1-3 Receive DL-Bit Register1-3)
- ------------------------ T1 ------------------------- */
-
-#define RDL1_RDL17 0x80
-#define RDL1_RDL16 0x40
-#define RDL1_RDL15 0x20
-#define RDL1_RDL14 0x10
-#define RDL1_RDL13 0x08
-#define RDL1_RDL12 0x04
-#define RDL1_RDL11 0x02
-#define RDL1_RDL10 0x01
-
-#define RDL2_RDL27 0x80
-#define RDL2_RDL26 0x40
-#define RDL2_RDL25 0x20
-#define RDL2_RDL24 0x10
-#define RDL2_RDL23 0x08
-#define RDL2_RDL22 0x04
-#define RDL2_RDL21 0x02
-#define RDL2_RDL20 0x01
-
-#define RDL3_RDL37 0x80
-#define RDL3_RDL36 0x40
-#define RDL3_RDL35 0x20
-#define RDL3_RDL34 0x10
-#define RDL3_RDL33 0x08
-#define RDL3_RDL32 0x04
-#define RDL3_RDL31 0x02
-#define RDL3_RDL30 0x01
-
-
-/* SIS (Signaling Status Register)
-
- -------------------- E1 & T1 -------------------------- */
-
-#define SIS_XDOV 0x80
-#define SIS_XFW 0x40
-#define SIS_XREP 0x20
-#define SIS_RLI 0x08
-#define SIS_CEC 0x04
-#define SIS_BOM 0x01
-
-
-/* RSIS (Receive Signaling Status Register)
-
- -------------------- E1 & T1 --------------------------- */
-
-#define RSIS_VFR 0x80
-#define RSIS_RDO 0x40
-#define RSIS_CRC16 0x20
-#define RSIS_RAB 0x10
-#define RSIS_HA1 0x08
-#define RSIS_HA0 0x04
-#define RSIS_HFR 0x02
-#define RSIS_LA 0x01
-
-
-/* RBCL/H (Receive Byte Count Low/High)
-
- ------------------- E1 & T1 ----------------------- */
-
-#define RBCL_RBC7 0x80
-#define RBCL_RBC6 0x40
-#define RBCL_RBC5 0x20
-#define RBCL_RBC4 0x10
-#define RBCL_RBC3 0x08
-#define RBCL_RBC2 0x04
-#define RBCL_RBC1 0x02
-#define RBCL_RBC0 0x01
-
-#define RBCH_OV 0x10
-#define RBCH_RBC11 0x08
-#define RBCH_RBC10 0x04
-#define RBCH_RBC9 0x02
-#define RBCH_RBC8 0x01
-
-
-/* ISR1-3 (Interrupt Status Register 1-3)
-
- ------------------ E1 & T1 ------------------------------ */
-
-#define FISR0_RME 0x80
-#define FISR0_RFS 0x40
-#define FISR0_T8MS 0x20
-#define FISR0_ISF 0x20
-#define FISR0_RMB 0x10
-#define FISR0_CASC 0x08
-#define FISR0_RSC 0x08
-#define FISR0_CRC6 0x04
-#define FISR0_CRC4 0x04
-#define FISR0_PDEN 0x02
-#define FISR0_RPF 0x01
-
-#define FISR1_CASE 0x80
-#define FISR1_LLBSC 0x80
-#define FISR1_RDO 0x40
-#define FISR1_ALLS 0x20
-#define FISR1_XDU 0x10
-#define FISR1_XMB 0x08
-#define FISR1_XLSC 0x02
-#define FISR1_XPR 0x01
-
-#define FISR2_FAR 0x80
-#define FISR2_LFA 0x40
-#define FISR2_MFAR 0x20
-#define FISR2_T400MS 0x10
-#define FISR2_LMFA 0x10
-#define FISR2_AIS 0x08
-#define FISR2_LOS 0x04
-#define FISR2_RAR 0x02
-#define FISR2_RA 0x01
-
-#define FISR3_ES 0x80
-#define FISR3_SEC 0x40
-#define FISR3_LMFA16 0x20
-#define FISR3_AIS16 0x10
-#define FISR3_RA16 0x08
-#define FISR3_API 0x04
-#define FISR3_XSLP 0x20
-#define FISR3_XSLN 0x10
-#define FISR3_LLBSC 0x08
-#define FISR3_XRS 0x04
-#define FISR3_SLN 0x02
-#define FISR3_SLP 0x01
-
-
-/* GIS (Global Interrupt Status Register)
-
- --------------------- E1 & T1 --------------------- */
-
-#define GIS_ISR3 0x08
-#define GIS_ISR2 0x04
-#define GIS_ISR1 0x02
-#define GIS_ISR0 0x01
-
-
-/* VSTR (Version Status Register)
-
- --------------------- E1 & T1 --------------------- */
-
-#define VSTR_VN3 0x08
-#define VSTR_VN2 0x04
-#define VSTR_VN1 0x02
-#define VSTR_VN0 0x01
-
-
-/*>>>>>>>>>>>>>>>>>>>>> Local Control Structures <<<<<<<<<<<<<<<<<<<<<<<<< */
-
-/* Write-only Registers (E1/T1 control mode write registers) */
-#define XFIFOH 0x00 /* Tx FIFO High Byte */
-#define XFIFOL 0x01 /* Tx FIFO Low Byte */
-#define CMDR 0x02 /* Command Reg */
-#define DEC 0x60 /* Disable Error Counter */
-#define TEST2 0x62 /* Manuf. Test Reg 2 */
-#define XS(nbr) (0x70 + (nbr)) /* Tx CAS Reg (0 to 15) */
-
-/* Read-write Registers (E1/T1 status mode read registers) */
-#define MODE 0x03 /* Mode Reg */
-#define RAH1 0x04 /* Receive Address High 1 */
-#define RAH2 0x05 /* Receive Address High 2 */
-#define RAL1 0x06 /* Receive Address Low 1 */
-#define RAL2 0x07 /* Receive Address Low 2 */
-#define IPC 0x08 /* Interrupt Port Configuration */
-#define CCR1 0x09 /* Common Configuration Reg 1 */
-#define CCR3 0x0A /* Common Configuration Reg 3 */
-#define PRE 0x0B /* Preamble Reg */
-#define RTR1 0x0C /* Receive Timeslot Reg 1 */
-#define RTR2 0x0D /* Receive Timeslot Reg 2 */
-#define RTR3 0x0E /* Receive Timeslot Reg 3 */
-#define RTR4 0x0F /* Receive Timeslot Reg 4 */
-#define TTR1 0x10 /* Transmit Timeslot Reg 1 */
-#define TTR2 0x11 /* Transmit Timeslot Reg 2 */
-#define TTR3 0x12 /* Transmit Timeslot Reg 3 */
-#define TTR4 0x13 /* Transmit Timeslot Reg 4 */
-#define IMR0 0x14 /* Interrupt Mask Reg 0 */
-#define IMR1 0x15 /* Interrupt Mask Reg 1 */
-#define IMR2 0x16 /* Interrupt Mask Reg 2 */
-#define IMR3 0x17 /* Interrupt Mask Reg 3 */
-#define IMR4 0x18 /* Interrupt Mask Reg 4 */
-#define IMR5 0x19 /* Interrupt Mask Reg 5 */
-#define FMR0 0x1A /* Framer Mode Reigster 0 */
-#define FMR1 0x1B /* Framer Mode Reigster 1 */
-#define FMR2 0x1C /* Framer Mode Reigster 2 */
-#define LOOP 0x1D /* Channel Loop Back */
-#define XSW 0x1E /* Transmit Service Word */
-#define FMR4 0x1E /* Framer Mode Reg 4 */
-#define XSP 0x1F /* Transmit Spare Bits */
-#define FMR5 0x1F /* Framer Mode Reg 5 */
-#define XC0 0x20 /* Transmit Control 0 */
-#define XC1 0x21 /* Transmit Control 1 */
-#define RC0 0x22 /* Receive Control 0 */
-#define RC1 0x23 /* Receive Control 1 */
-#define XPM0 0x24 /* Transmit Pulse Mask 0 */
-#define XPM1 0x25 /* Transmit Pulse Mask 1 */
-#define XPM2 0x26 /* Transmit Pulse Mask 2 */
-#define TSWM 0x27 /* Transparent Service Word Mask */
-#define TEST1 0x28 /* Manuf. Test Reg 1 */
-#define IDLE 0x29 /* Idle Channel Code */
-#define XSA4 0x2A /* Transmit SA4 Bit Reg */
-#define XDL1 0x2A /* Transmit DL-Bit Reg 2 */
-#define XSA5 0x2B /* Transmit SA4 Bit Reg */
-#define XDL2 0x2B /* Transmit DL-Bit Reg 2 */
-#define XSA6 0x2C /* Transmit SA4 Bit Reg */
-#define XDL3 0x2C /* Transmit DL-Bit Reg 2 */
-#define XSA7 0x2D /* Transmit SA4 Bit Reg */
-#define CCB1 0x2D /* Clear Channel Reg 1 */
-#define XSA8 0x2E /* Transmit SA4 Bit Reg */
-#define CCB2 0x2E /* Clear Channel Reg 2 */
-#define FMR3 0x2F /* Framer Mode Reg. 3 */
-#define CCB3 0x2F /* Clear Channel Reg 3 */
-#define ICB1 0x30 /* Idle Channel Reg 1 */
-#define ICB2 0x31 /* Idle Channel Reg 2 */
-#define ICB3 0x32 /* Idle Channel Reg 3 */
-#define ICB4 0x33 /* Idle Channel Reg 4 */
-#define LIM0 0x34 /* Line Interface Mode 0 */
-#define LIM1 0x35 /* Line Interface Mode 1 */
-#define PCDR 0x36 /* Pulse Count Detection */
-#define PCRR 0x37 /* Pulse Count Recovery */
-#define LIM2 0x38 /* Line Interface Mode Reg 2 */
-#define LCR1 0x39 /* Loop Code Reg 1 */
-#define LCR2 0x3A /* Loop Code Reg 2 */
-#define LCR3 0x3B /* Loop Code Reg 3 */
-#define SIC1 0x3C /* System Interface Control 1 */
-
-/* Read-only Registers (E1/T1 control mode read registers) */
-#define RFIFOH 0x00 /* Receive FIFO */
-#define RFIFOL 0x01 /* Receive FIFO */
-#define FRS0 0x4C /* Framer Receive Status 0 */
-#define FRS1 0x4D /* Framer Receive Status 1 */
-#define RSW 0x4E /* Receive Service Word */
-#define FRS2 0x4E /* Framer Receive Status 2 */
-#define RSP 0x4F /* Receive Spare Bits */
-#define FRS3 0x4F /* Framer Receive Status 3 */
-#define FECL 0x50 /* Framing Error Counter */
-#define FECH 0x51 /* Framing Error Counter */
-#define CVCL 0x52 /* Code Violation Counter */
-#define CVCH 0x53 /* Code Violation Counter */
-#define CECL 0x54 /* CRC Error Counter 1 */
-#define CECH 0x55 /* CRC Error Counter 1 */
-#define EBCL 0x56 /* E-Bit Error Counter */
-#define EBCH 0x57 /* E-Bit Error Counter */
-#define BECL 0x58 /* Bit Error Counter Low */
-#define BECH 0x59 /* Bit Error Counter Low */
-#define CEC3 0x5A /* CRC Error Counter 3 (16-bit) */
-#define RSA4 0x5C /* Receive SA4 Bit Reg */
-#define RDL1 0x5C /* Receive DL-Bit Reg 1 */
-#define RSA5 0x5D /* Receive SA5 Bit Reg */
-#define RDL2 0x5D /* Receive DL-Bit Reg 2 */
-#define RSA6 0x5E /* Receive SA6 Bit Reg */
-#define RDL3 0x5E /* Receive DL-Bit Reg 3 */
-#define RSA7 0x5F /* Receive SA7 Bit Reg */
-#define RSA8 0x60 /* Receive SA8 Bit Reg */
-#define RSA6S 0x61 /* Receive SA6 Bit Status Reg */
-#define TSR0 0x62 /* Manuf. Test Reg 0 */
-#define TSR1 0x63 /* Manuf. Test Reg 1 */
-#define SIS 0x64 /* Signaling Status Reg */
-#define RSIS 0x65 /* Receive Signaling Status Reg */
-#define RBCL 0x66 /* Receive Byte Control */
-#define RBCH 0x67 /* Receive Byte Control */
-#define FISR0 0x68 /* Interrupt Status Reg 0 */
-#define FISR1 0x69 /* Interrupt Status Reg 1 */
-#define FISR2 0x6A /* Interrupt Status Reg 2 */
-#define FISR3 0x6B /* Interrupt Status Reg 3 */
-#define GIS 0x6E /* Global Interrupt Status */
-#define VSTR 0x6F /* Version Status */
-#define RS(nbr) (0x70 + (nbr)) /* Rx CAS Reg (0 to 15) */
-
-#endif /* _FALC_LH_H */
-
diff --git a/drivers/net/wan/pc300.h b/drivers/net/wan/pc300.h
deleted file mode 100644
index 2e4f84f6cad4..000000000000
--- a/drivers/net/wan/pc300.h
+++ /dev/null
@@ -1,436 +0,0 @@
-/*
- * pc300.h Cyclades-PC300(tm) Kernel API Definitions.
- *
- * Author: Ivan Passos <ivan@cyclades.com>
- *
- * Copyright: (c) 1999-2002 Cyclades Corp.
- *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License
- * as published by the Free Software Foundation; either version
- * 2 of the License, or (at your option) any later version.
- *
- * $Log: pc300.h,v $
- * Revision 3.12 2002/03/07 14:17:09 henrique
- * License data fixed
- *
- * Revision 3.11 2002/01/28 21:09:39 daniela
- * Included ';' after pc300hw.bus.
- *
- * Revision 3.10 2002/01/17 17:58:52 ivan
- * Support for PC300-TE/M (PMC).
- *
- * Revision 3.9 2001/09/28 13:30:53 daniela
- * Renamed dma_start routine to rx_dma_start.
- *
- * Revision 3.8 2001/09/24 13:03:45 daniela
- * Fixed BOF interrupt treatment. Created dma_start routine.
- *
- * Revision 3.7 2001/08/10 17:19:58 daniela
- * Fixed IOCTLs defines.
- *
- * Revision 3.6 2001/07/18 19:24:42 daniela
- * Included kernel version.
- *
- * Revision 3.5 2001/07/05 18:38:08 daniela
- * DMA transmission bug fix.
- *
- * Revision 3.4 2001/06/26 17:10:40 daniela
- * New configuration parameters (line code, CRC calculation and clock).
- *
- * Revision 3.3 2001/06/22 13:13:02 regina
- * MLPPP implementation
- *
- * Revision 3.2 2001/06/18 17:56:09 daniela
- * Increased DEF_MTU and TX_QUEUE_LEN.
- *
- * Revision 3.1 2001/06/15 12:41:10 regina
- * upping major version number
- *
- * Revision 1.1.1.1 2001/06/13 20:25:06 daniela
- * PC300 initial CVS version (3.4.0-pre1)
- *
- * Revision 2.3 2001/03/05 daniela
- * Created struct pc300conf, to provide the hardware information to pc300util.
- * Inclusion of 'alloc_ramsize' field on structure 'pc300hw'.
- *
- * Revision 2.2 2000/12/22 daniela
- * Structures and defines to support pc300util: statistics, status,
- * loopback tests, trace.
- *
- * Revision 2.1 2000/09/28 ivan
- * Inclusion of 'iophys' and 'iosize' fields on structure 'pc300hw', to
- * allow release of I/O region at module unload.
- * Changed location of include files.
- *
- * Revision 2.0 2000/03/27 ivan
- * Added support for the PC300/TE cards.
- *
- * Revision 1.1 2000/01/31 ivan
- * Replaced 'pc300[drv|sca].h' former PC300 driver include files.
- *
- * Revision 1.0 1999/12/16 ivan
- * First official release.
- * Inclusion of 'nchan' field on structure 'pc300hw', to allow variable
- * number of ports per card.
- * Inclusion of 'if_ptr' field on structure 'pc300dev'.
- *
- * Revision 0.6 1999/11/17 ivan
- * Changed X.25-specific function names to comply with adopted convention.
- *
- * Revision 0.5 1999/11/16 Daniela Squassoni
- * X.25 support.
- *
- * Revision 0.4 1999/11/15 ivan
- * Inclusion of 'clock' field on structure 'pc300hw'.
- *
- * Revision 0.3 1999/11/10 ivan
- * IOCTL name changing.
- * Inclusion of driver function prototypes.
- *
- * Revision 0.2 1999/11/03 ivan
- * Inclusion of 'tx_skb' and union 'ifu' on structure 'pc300dev'.
- *
- * Revision 0.1 1999/01/15 ivan
- * Initial version.
- *
- */
-
-#ifndef _PC300_H
-#define _PC300_H
-
-#include <linux/hdlc.h>
-#include "hd64572.h"
-#include "pc300-falc-lh.h"
-
-#define PC300_PROTO_MLPPP 1
-
-#define PC300_MAXCHAN 2 /* Number of channels per card */
-
-#define PC300_RAMSIZE 0x40000 /* RAM window size (256Kb) */
-#define PC300_FALCSIZE 0x400 /* FALC window size (1Kb) */
-
-#define PC300_OSC_CLOCK 24576000
-#define PC300_PCI_CLOCK 33000000
-
-#define BD_DEF_LEN 0x0800 /* DMA buffer length (2KB) */
-#define DMA_TX_MEMSZ 0x8000 /* Total DMA Tx memory size (32KB/ch) */
-#define DMA_RX_MEMSZ 0x10000 /* Total DMA Rx memory size (64KB/ch) */
-
-#define N_DMA_TX_BUF (DMA_TX_MEMSZ / BD_DEF_LEN) /* DMA Tx buffers */
-#define N_DMA_RX_BUF (DMA_RX_MEMSZ / BD_DEF_LEN) /* DMA Rx buffers */
-
-/* DMA Buffer Offsets */
-#define DMA_TX_BASE ((N_DMA_TX_BUF + N_DMA_RX_BUF) * \
- PC300_MAXCHAN * sizeof(pcsca_bd_t))
-#define DMA_RX_BASE (DMA_TX_BASE + PC300_MAXCHAN*DMA_TX_MEMSZ)
-
-/* DMA Descriptor Offsets */
-#define DMA_TX_BD_BASE 0x0000
-#define DMA_RX_BD_BASE (DMA_TX_BD_BASE + ((PC300_MAXCHAN*DMA_TX_MEMSZ / \
- BD_DEF_LEN) * sizeof(pcsca_bd_t)))
-
-/* DMA Descriptor Macros */
-#define TX_BD_ADDR(chan, n) (DMA_TX_BD_BASE + \
- ((N_DMA_TX_BUF*chan) + n) * sizeof(pcsca_bd_t))
-#define RX_BD_ADDR(chan, n) (DMA_RX_BD_BASE + \
- ((N_DMA_RX_BUF*chan) + n) * sizeof(pcsca_bd_t))
-
-/* Macro to access the FALC registers (TE only) */
-#define F_REG(reg, chan) (0x200*(chan) + ((reg)<<2))
-
-/***************************************
- * Memory access functions/macros *
- * (required to support Alpha systems) *
- ***************************************/
-#define cpc_writeb(port,val) {writeb((u8)(val),(port)); mb();}
-#define cpc_writew(port,val) {writew((ushort)(val),(port)); mb();}
-#define cpc_writel(port,val) {writel((u32)(val),(port)); mb();}
-
-#define cpc_readb(port) readb(port)
-#define cpc_readw(port) readw(port)
-#define cpc_readl(port) readl(port)
-
-/****** Data Structures *****************************************************/
-
-/*
- * RUNTIME_9050 - PLX PCI9050-1 local configuration and shared runtime
- * registers. This structure can be used to access the 9050 registers
- * (memory mapped).
- */
-struct RUNTIME_9050 {
- u32 loc_addr_range[4]; /* 00-0Ch : Local Address Ranges */
- u32 loc_rom_range; /* 10h : Local ROM Range */
- u32 loc_addr_base[4]; /* 14-20h : Local Address Base Addrs */
- u32 loc_rom_base; /* 24h : Local ROM Base */
- u32 loc_bus_descr[4]; /* 28-34h : Local Bus Descriptors */
- u32 rom_bus_descr; /* 38h : ROM Bus Descriptor */
- u32 cs_base[4]; /* 3C-48h : Chip Select Base Addrs */
- u32 intr_ctrl_stat; /* 4Ch : Interrupt Control/Status */
- u32 init_ctrl; /* 50h : EEPROM ctrl, Init Ctrl, etc */
-};
-
-#define PLX_9050_LINT1_ENABLE 0x01
-#define PLX_9050_LINT1_POL 0x02
-#define PLX_9050_LINT1_STATUS 0x04
-#define PLX_9050_LINT2_ENABLE 0x08
-#define PLX_9050_LINT2_POL 0x10
-#define PLX_9050_LINT2_STATUS 0x20
-#define PLX_9050_INTR_ENABLE 0x40
-#define PLX_9050_SW_INTR 0x80
-
-/* Masks to access the init_ctrl PLX register */
-#define PC300_CLKSEL_MASK (0x00000004UL)
-#define PC300_CHMEDIA_MASK(chan) (0x00000020UL<<(chan*3))
-#define PC300_CTYPE_MASK (0x00000800UL)
-
-/* CPLD Registers (base addr = falcbase, TE only) */
-/* CPLD v. 0 */
-#define CPLD_REG1 0x140 /* Chip resets, DCD/CTS status */
-#define CPLD_REG2 0x144 /* Clock enable , LED control */
-/* CPLD v. 2 or higher */
-#define CPLD_V2_REG1 0x100 /* Chip resets, DCD/CTS status */
-#define CPLD_V2_REG2 0x104 /* Clock enable , LED control */
-#define CPLD_ID_REG 0x108 /* CPLD version */
-
-/* CPLD Register bit description: for the FALC bits, they should always be
- set based on the channel (use (bit<<(2*ch)) to access the correct bit for
- that channel) */
-#define CPLD_REG1_FALC_RESET 0x01
-#define CPLD_REG1_SCA_RESET 0x02
-#define CPLD_REG1_GLOBAL_CLK 0x08
-#define CPLD_REG1_FALC_DCD 0x10
-#define CPLD_REG1_FALC_CTS 0x20
-
-#define CPLD_REG2_FALC_TX_CLK 0x01
-#define CPLD_REG2_FALC_RX_CLK 0x02
-#define CPLD_REG2_FALC_LED1 0x10
-#define CPLD_REG2_FALC_LED2 0x20
-
-/* Structure with FALC-related fields (TE only) */
-#define PC300_FALC_MAXLOOP 0x0000ffff /* for falc_issue_cmd() */
-
-typedef struct falc {
- u8 sync; /* If true FALC is synchronized */
- u8 active; /* if TRUE then already active */
- u8 loop_active; /* if TRUE a line loopback UP was received */
- u8 loop_gen; /* if TRUE a line loopback UP was issued */
-
- u8 num_channels;
- u8 offset; /* 1 for T1, 0 for E1 */
- u8 full_bandwidth;
-
- u8 xmb_cause;
- u8 multiframe_mode;
-
- /* Statistics */
- u16 pden; /* Pulse Density violation count */
- u16 los; /* Loss of Signal count */
- u16 losr; /* Loss of Signal recovery count */
- u16 lfa; /* Loss of frame alignment count */
- u16 farec; /* Frame Alignment Recovery count */
- u16 lmfa; /* Loss of multiframe alignment count */
- u16 ais; /* Remote Alarm indication Signal count */
- u16 sec; /* One-second timer */
- u16 es; /* Errored second */
- u16 rai; /* remote alarm received */
- u16 bec;
- u16 fec;
- u16 cvc;
- u16 cec;
- u16 ebc;
-
- /* Status */
- u8 red_alarm;
- u8 blue_alarm;
- u8 loss_fa;
- u8 yellow_alarm;
- u8 loss_mfa;
- u8 prbs;
-} falc_t;
-
-typedef struct falc_status {
- u8 sync; /* If true FALC is synchronized */
- u8 red_alarm;
- u8 blue_alarm;
- u8 loss_fa;
- u8 yellow_alarm;
- u8 loss_mfa;
- u8 prbs;
-} falc_status_t;
-
-typedef struct rsv_x21_status {
- u8 dcd;
- u8 dsr;
- u8 cts;
- u8 rts;
- u8 dtr;
-} rsv_x21_status_t;
-
-typedef struct pc300stats {
- int hw_type;
- u32 line_on;
- u32 line_off;
- struct net_device_stats gen_stats;
- falc_t te_stats;
-} pc300stats_t;
-
-typedef struct pc300status {
- int hw_type;
- rsv_x21_status_t gen_status;
- falc_status_t te_status;
-} pc300status_t;
-
-typedef struct pc300loopback {
- char loop_type;
- char loop_on;
-} pc300loopback_t;
-
-typedef struct pc300patterntst {
- char patrntst_on; /* 0 - off; 1 - on; 2 - read num_errors */
- u16 num_errors;
-} pc300patterntst_t;
-
-typedef struct pc300dev {
- struct pc300ch *chan;
- u8 trace_on;
- u32 line_on; /* DCD(X.21, RSV) / sync(TE) change counters */
- u32 line_off;
- char name[16];
- struct net_device *dev;
-#ifdef CONFIG_PC300_MLPPP
- void *cpc_tty; /* information to PC300 TTY driver */
-#endif
-}pc300dev_t;
-
-typedef struct pc300hw {
- int type; /* RSV, X21, etc. */
- int bus; /* Bus (PCI, PMC, etc.) */
- int nchan; /* number of channels */
- int irq; /* interrupt request level */
- u32 clock; /* Board clock */
- u8 cpld_id; /* CPLD ID (TE only) */
- u16 cpld_reg1; /* CPLD reg 1 (TE only) */
- u16 cpld_reg2; /* CPLD reg 2 (TE only) */
- u16 gpioc_reg; /* PLX GPIOC reg */
- u16 intctl_reg; /* PLX Int Ctrl/Status reg */
- u32 iophys; /* PLX registers I/O base */
- u32 iosize; /* PLX registers I/O size */
- u32 plxphys; /* PLX registers MMIO base (physical) */
- void __iomem * plxbase; /* PLX registers MMIO base (virtual) */
- u32 plxsize; /* PLX registers MMIO size */
- u32 scaphys; /* SCA registers MMIO base (physical) */
- void __iomem * scabase; /* SCA registers MMIO base (virtual) */
- u32 scasize; /* SCA registers MMIO size */
- u32 ramphys; /* On-board RAM MMIO base (physical) */
- void __iomem * rambase; /* On-board RAM MMIO base (virtual) */
- u32 alloc_ramsize; /* RAM MMIO size allocated by the PCI bridge */
- u32 ramsize; /* On-board RAM MMIO size */
- u32 falcphys; /* FALC registers MMIO base (physical) */
- void __iomem * falcbase;/* FALC registers MMIO base (virtual) */
- u32 falcsize; /* FALC registers MMIO size */
-} pc300hw_t;
-
-typedef struct pc300chconf {
- sync_serial_settings phys_settings; /* Clock type/rate (in bps),
- loopback mode */
- raw_hdlc_proto proto_settings; /* Encoding, parity (CRC) */
- u32 media; /* HW media (RS232, V.35, etc.) */
- u32 proto; /* Protocol (PPP, X.25, etc.) */
-
- /* TE-specific parameters */
- u8 lcode; /* Line Code (AMI, B8ZS, etc.) */
- u8 fr_mode; /* Frame Mode (ESF, D4, etc.) */
- u8 lbo; /* Line Build Out */
- u8 rx_sens; /* Rx Sensitivity (long- or short-haul) */
- u32 tslot_bitmap; /* bit[i]=1 => timeslot _i_ is active */
-} pc300chconf_t;
-
-typedef struct pc300ch {
- struct pc300 *card;
- int channel;
- pc300dev_t d;
- pc300chconf_t conf;
- u8 tx_first_bd; /* First TX DMA block descr. w/ data */
- u8 tx_next_bd; /* Next free TX DMA block descriptor */
- u8 rx_first_bd; /* First free RX DMA block descriptor */
- u8 rx_last_bd; /* Last free RX DMA block descriptor */
- u8 nfree_tx_bd; /* Number of free TX DMA block descriptors */
- falc_t falc; /* FALC structure (TE only) */
-} pc300ch_t;
-
-typedef struct pc300 {
- pc300hw_t hw; /* hardware config. */
- pc300ch_t chan[PC300_MAXCHAN];
- spinlock_t card_lock;
-} pc300_t;
-
-typedef struct pc300conf {
- pc300hw_t hw;
- pc300chconf_t conf;
-} pc300conf_t;
-
-/* DEV ioctl() commands */
-#define N_SPPP_IOCTLS 2
-
-enum pc300_ioctl_cmds {
- SIOCCPCRESERVED = (SIOCDEVPRIVATE + N_SPPP_IOCTLS),
- SIOCGPC300CONF,
- SIOCSPC300CONF,
- SIOCGPC300STATUS,
- SIOCGPC300FALCSTATUS,
- SIOCGPC300UTILSTATS,
- SIOCGPC300UTILSTATUS,
- SIOCSPC300TRACE,
- SIOCSPC300LOOPBACK,
- SIOCSPC300PATTERNTEST,
-};
-
-/* Loopback types - PC300/TE boards */
-enum pc300_loopback_cmds {
- PC300LOCLOOP = 1,
- PC300REMLOOP,
- PC300PAYLOADLOOP,
- PC300GENLOOPUP,
- PC300GENLOOPDOWN,
-};
-
-/* Control Constant Definitions */
-#define PC300_RSV 0x01
-#define PC300_X21 0x02
-#define PC300_TE 0x03
-
-#define PC300_PCI 0x00
-#define PC300_PMC 0x01
-
-#define PC300_LC_AMI 0x01
-#define PC300_LC_B8ZS 0x02
-#define PC300_LC_NRZ 0x03
-#define PC300_LC_HDB3 0x04
-
-/* Framing (T1) */
-#define PC300_FR_ESF 0x01
-#define PC300_FR_D4 0x02
-#define PC300_FR_ESF_JAPAN 0x03
-
-/* Framing (E1) */
-#define PC300_FR_MF_CRC4 0x04
-#define PC300_FR_MF_NON_CRC4 0x05
-#define PC300_FR_UNFRAMED 0x06
-
-#define PC300_LBO_0_DB 0x00
-#define PC300_LBO_7_5_DB 0x01
-#define PC300_LBO_15_DB 0x02
-#define PC300_LBO_22_5_DB 0x03
-
-#define PC300_RX_SENS_SH 0x01
-#define PC300_RX_SENS_LH 0x02
-
-#define PC300_TX_TIMEOUT (2*HZ)
-#define PC300_TX_QUEUE_LEN 100
-#define PC300_DEF_MTU 1600
-
-/* Function Prototypes */
-int cpc_open(struct net_device *dev);
-
-#endif /* _PC300_H */
diff --git a/drivers/net/wan/pc300_drv.c b/drivers/net/wan/pc300_drv.c
deleted file mode 100644
index cb0f8d932b0c..000000000000
--- a/drivers/net/wan/pc300_drv.c
+++ /dev/null
@@ -1,3670 +0,0 @@
-#define USE_PCI_CLOCK
-static const char rcsid[] =
-"Revision: 3.4.5 Date: 2002/03/07 ";
-
-/*
- * pc300.c Cyclades-PC300(tm) Driver.
- *
- * Author: Ivan Passos <ivan@cyclades.com>
- * Maintainer: PC300 Maintainer <pc300@cyclades.com>
- *
- * Copyright: (c) 1999-2003 Cyclades Corp.
- *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License
- * as published by the Free Software Foundation; either version
- * 2 of the License, or (at your option) any later version.
- *
- * Using tabstop = 4.
- *
- * $Log: pc300_drv.c,v $
- * Revision 3.23 2002/03/20 13:58:40 henrique
- * Fixed ortographic mistakes
- *
- * Revision 3.22 2002/03/13 16:56:56 henrique
- * Take out the debug messages
- *
- * Revision 3.21 2002/03/07 14:17:09 henrique
- * License data fixed
- *
- * Revision 3.20 2002/01/17 17:58:52 ivan
- * Support for PC300-TE/M (PMC).
- *
- * Revision 3.19 2002/01/03 17:08:47 daniela
- * Enables DMA reception when the SCA-II disables it improperly.
- *
- * Revision 3.18 2001/12/03 18:47:50 daniela
- * Esthetic changes.
- *
- * Revision 3.17 2001/10/19 16:50:13 henrique
- * Patch to kernel 2.4.12 and new generic hdlc.
- *
- * Revision 3.16 2001/10/16 15:12:31 regina
- * clear statistics
- *
- * Revision 3.11 to 3.15 2001/10/11 20:26:04 daniela
- * More DMA fixes for noisy lines.
- * Return the size of bad frames in dma_get_rx_frame_size, so that the Rx buffer
- * descriptors can be cleaned by dma_buf_read (called in cpc_net_rx).
- * Renamed dma_start routine to rx_dma_start. Improved Rx statistics.
- * Fixed BOF interrupt treatment. Created dma_start routine.
- * Changed min and max to cpc_min and cpc_max.
- *
- * Revision 3.10 2001/08/06 12:01:51 regina
- * Fixed problem in DSR_DE bit.
- *
- * Revision 3.9 2001/07/18 19:27:26 daniela
- * Added some history comments.
- *
- * Revision 3.8 2001/07/12 13:11:19 regina
- * bug fix - DCD-OFF in pc300 tty driver
- *
- * Revision 3.3 to 3.7 2001/07/06 15:00:20 daniela
- * Removing kernel 2.4.3 and previous support.
- * DMA transmission bug fix.
- * MTU check in cpc_net_rx fixed.
- * Boot messages reviewed.
- * New configuration parameters (line code, CRC calculation and clock).
- *
- * Revision 3.2 2001/06/22 13:13:02 regina
- * MLPPP implementation. Changed the header of message trace to include
- * the device name. New format : "hdlcX[R/T]: ".
- * Default configuration changed.
- *
- * Revision 3.1 2001/06/15 regina
- * in cpc_queue_xmit, netif_stop_queue is called if don't have free descriptor
- * upping major version number
- *
- * Revision 1.1.1.1 2001/06/13 20:25:04 daniela
- * PC300 initial CVS version (3.4.0-pre1)
- *
- * Revision 3.0.1.2 2001/06/08 daniela
- * Did some changes in the DMA programming implementation to avoid the
- * occurrence of a SCA-II bug when CDA is accessed during a DMA transfer.
- *
- * Revision 3.0.1.1 2001/05/02 daniela
- * Added kernel 2.4.3 support.
- *
- * Revision 3.0.1.0 2001/03/13 daniela, henrique
- * Added Frame Relay Support.
- * Driver now uses HDLC generic driver to provide protocol support.
- *
- * Revision 3.0.0.8 2001/03/02 daniela
- * Fixed ram size detection.
- * Changed SIOCGPC300CONF ioctl, to give hw information to pc300util.
- *
- * Revision 3.0.0.7 2001/02/23 daniela
- * netif_stop_queue called before the SCA-II transmition commands in
- * cpc_queue_xmit, and with interrupts disabled to avoid race conditions with
- * transmition interrupts.
- * Fixed falc_check_status for Unframed E1.
- *
- * Revision 3.0.0.6 2000/12/13 daniela
- * Implemented pc300util support: trace, statistics, status and loopback
- * tests for the PC300 TE boards.
- *
- * Revision 3.0.0.5 2000/12/12 ivan
- * Added support for Unframed E1.
- * Implemented monitor mode.
- * Fixed DCD sensitivity on the second channel.
- * Driver now complies with new PCI kernel architecture.
- *
- * Revision 3.0.0.4 2000/09/28 ivan
- * Implemented DCD sensitivity.
- * Moved hardware-specific open to the end of cpc_open, to avoid race
- * conditions with early reception interrupts.
- * Included code for [request|release]_mem_region().
- * Changed location of pc300.h .
- * Minor code revision (contrib. of Jeff Garzik).
- *
- * Revision 3.0.0.3 2000/07/03 ivan
- * Previous bugfix for the framing errors with external clock made X21
- * boards stop working. This version fixes it.
- *
- * Revision 3.0.0.2 2000/06/23 ivan
- * Revisited cpc_queue_xmit to prevent race conditions on Tx DMA buffer
- * handling when Tx timeouts occur.
- * Revisited Rx statistics.
- * Fixed a bug in the SCA-II programming that would cause framing errors
- * when external clock was configured.
- *
- * Revision 3.0.0.1 2000/05/26 ivan
- * Added logic in the SCA interrupt handler so that no board can monopolize
- * the driver.
- * Request PLX I/O region, although driver doesn't use it, to avoid
- * problems with other drivers accessing it.
- *
- * Revision 3.0.0.0 2000/05/15 ivan
- * Did some changes in the DMA programming implementation to avoid the
- * occurrence of a SCA-II bug in the second channel.
- * Implemented workaround for PLX9050 bug that would cause a system lockup
- * in certain systems, depending on the MMIO addresses allocated to the
- * board.
- * Fixed the FALC chip programming to avoid synchronization problems in the
- * second channel (TE only).
- * Implemented a cleaner and faster Tx DMA descriptor cleanup procedure in
- * cpc_queue_xmit().
- * Changed the built-in driver implementation so that the driver can use the
- * general 'hdlcN' naming convention instead of proprietary device names.
- * Driver load messages are now device-centric, instead of board-centric.
- * Dynamic allocation of net_device structures.
- * Code is now compliant with the new module interface (module_[init|exit]).
- * Make use of the PCI helper functions to access PCI resources.
- *
- * Revision 2.0.0.0 2000/04/15 ivan
- * Added support for the PC300/TE boards (T1/FT1/E1/FE1).
- *
- * Revision 1.1.0.0 2000/02/28 ivan
- * Major changes in the driver architecture.
- * Softnet compliancy implemented.
- * Driver now reports physical instead of virtual memory addresses.
- * Added cpc_change_mtu function.
- *
- * Revision 1.0.0.0 1999/12/16 ivan
- * First official release.
- * Support for 1- and 2-channel boards (which use distinct PCI Device ID's).
- * Support for monolythic installation (i.e., drv built into the kernel).
- * X.25 additional checking when lapb_[dis]connect_request returns an error.
- * SCA programming now covers X.21 as well.
- *
- * Revision 0.3.1.0 1999/11/18 ivan
- * Made X.25 support configuration-dependent (as it depends on external
- * modules to work).
- * Changed X.25-specific function names to comply with adopted convention.
- * Fixed typos in X.25 functions that would cause compile errors (Daniela).
- * Fixed bug in ch_config that would disable interrupts on a previously
- * enabled channel if the other channel on the same board was enabled later.
- *
- * Revision 0.3.0.0 1999/11/16 daniela
- * X.25 support.
- *
- * Revision 0.2.3.0 1999/11/15 ivan
- * Function cpc_ch_status now provides more detailed information.
- * Added support for X.21 clock configuration.
- * Changed TNR1 setting in order to prevent Tx FIFO overaccesses by the SCA.
- * Now using PCI clock instead of internal oscillator clock for the SCA.
- *
- * Revision 0.2.2.0 1999/11/10 ivan
- * Changed the *_dma_buf_check functions so that they would print only
- * the useful info instead of the whole buffer descriptor bank.
- * Fixed bug in cpc_queue_xmit that would eventually crash the system
- * in case of a packet drop.
- * Implemented TX underrun handling.
- * Improved SCA fine tuning to boost up its performance.
- *
- * Revision 0.2.1.0 1999/11/03 ivan
- * Added functions *dma_buf_pt_init to allow independent initialization
- * of the next-descr. and DMA buffer pointers on the DMA descriptors.
- * Kernel buffer release and tbusy clearing is now done in the interrupt
- * handler.
- * Fixed bug in cpc_open that would cause an interface reopen to fail.
- * Added a protocol-specific code section in cpc_net_rx.
- * Removed printk level defs (they might be added back after the beta phase).
- *
- * Revision 0.2.0.0 1999/10/28 ivan
- * Revisited the code so that new protocols can be easily added / supported.
- *
- * Revision 0.1.0.1 1999/10/20 ivan
- * Mostly "esthetic" changes.
- *
- * Revision 0.1.0.0 1999/10/11 ivan
- * Initial version.
- *
- */
-
-#define pr_fmt(fmt) KBUILD_MODNAME ": " fmt
-
-#include <linux/module.h>
-#include <linux/kernel.h>
-#include <linux/mm.h>
-#include <linux/ioport.h>
-#include <linux/pci.h>
-#include <linux/errno.h>
-#include <linux/string.h>
-#include <linux/init.h>
-#include <linux/delay.h>
-#include <linux/net.h>
-#include <linux/skbuff.h>
-#include <linux/if_arp.h>
-#include <linux/netdevice.h>
-#include <linux/etherdevice.h>
-#include <linux/spinlock.h>
-#include <linux/if.h>
-#include <linux/slab.h>
-#include <net/arp.h>
-
-#include <asm/io.h>
-#include <asm/uaccess.h>
-
-#include "pc300.h"
-
-#define CPC_LOCK(card,flags) \
- do { \
- spin_lock_irqsave(&card->card_lock, flags); \
- } while (0)
-
-#define CPC_UNLOCK(card,flags) \
- do { \
- spin_unlock_irqrestore(&card->card_lock, flags); \
- } while (0)
-
-#undef PC300_DEBUG_PCI
-#undef PC300_DEBUG_INTR
-#undef PC300_DEBUG_TX
-#undef PC300_DEBUG_RX
-#undef PC300_DEBUG_OTHER
-
-static DEFINE_PCI_DEVICE_TABLE(cpc_pci_dev_id) = {
- /* PC300/RSV or PC300/X21, 2 chan */
- {0x120e, 0x300, PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0x300},
- /* PC300/RSV or PC300/X21, 1 chan */
- {0x120e, 0x301, PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0x301},
- /* PC300/TE, 2 chan */
- {0x120e, 0x310, PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0x310},
- /* PC300/TE, 1 chan */
- {0x120e, 0x311, PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0x311},
- /* PC300/TE-M, 2 chan */
- {0x120e, 0x320, PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0x320},
- /* PC300/TE-M, 1 chan */
- {0x120e, 0x321, PCI_ANY_ID, PCI_ANY_ID, 0, 0, 0x321},
- /* End of table */
- {0,},
-};
-MODULE_DEVICE_TABLE(pci, cpc_pci_dev_id);
-
-#ifndef cpc_min
-#define cpc_min(a,b) (((a)<(b))?(a):(b))
-#endif
-#ifndef cpc_max
-#define cpc_max(a,b) (((a)>(b))?(a):(b))
-#endif
-
-/* prototypes */
-static void tx_dma_buf_pt_init(pc300_t *, int);
-static void tx_dma_buf_init(pc300_t *, int);
-static void rx_dma_buf_pt_init(pc300_t *, int);
-static void rx_dma_buf_init(pc300_t *, int);
-static void tx_dma_buf_check(pc300_t *, int);
-static void rx_dma_buf_check(pc300_t *, int);
-static irqreturn_t cpc_intr(int, void *);
-static int clock_rate_calc(u32, u32, int *);
-static u32 detect_ram(pc300_t *);
-static void plx_init(pc300_t *);
-static void cpc_trace(struct net_device *, struct sk_buff *, char);
-static int cpc_attach(struct net_device *, unsigned short, unsigned short);
-static int cpc_close(struct net_device *dev);
-
-#ifdef CONFIG_PC300_MLPPP
-void cpc_tty_init(pc300dev_t * dev);
-void cpc_tty_unregister_service(pc300dev_t * pc300dev);
-void cpc_tty_receive(pc300dev_t * pc300dev);
-void cpc_tty_trigger_poll(pc300dev_t * pc300dev);
-#endif
-
-/************************/
-/*** DMA Routines ***/
-/************************/
-static void tx_dma_buf_pt_init(pc300_t * card, int ch)
-{
- int i;
- int ch_factor = ch * N_DMA_TX_BUF;
- volatile pcsca_bd_t __iomem *ptdescr = (card->hw.rambase
- + DMA_TX_BD_BASE + ch_factor * sizeof(pcsca_bd_t));
-
- for (i = 0; i < N_DMA_TX_BUF; i++, ptdescr++) {
- cpc_writel(&ptdescr->next, (u32)(DMA_TX_BD_BASE +
- (ch_factor + ((i + 1) & (N_DMA_TX_BUF - 1))) * sizeof(pcsca_bd_t)));
- cpc_writel(&ptdescr->ptbuf,
- (u32)(DMA_TX_BASE + (ch_factor + i) * BD_DEF_LEN));
- }
-}
-
-static void tx_dma_buf_init(pc300_t * card, int ch)
-{
- int i;
- int ch_factor = ch * N_DMA_TX_BUF;
- volatile pcsca_bd_t __iomem *ptdescr = (card->hw.rambase
- + DMA_TX_BD_BASE + ch_factor * sizeof(pcsca_bd_t));
-
- for (i = 0; i < N_DMA_TX_BUF; i++, ptdescr++) {
- memset_io(ptdescr, 0, sizeof(pcsca_bd_t));
- cpc_writew(&ptdescr->len, 0);
- cpc_writeb(&ptdescr->status, DST_OSB);
- }
- tx_dma_buf_pt_init(card, ch);
-}
-
-static void rx_dma_buf_pt_init(pc300_t * card, int ch)
-{
- int i;
- int ch_factor = ch * N_DMA_RX_BUF;
- volatile pcsca_bd_t __iomem *ptdescr = (card->hw.rambase
- + DMA_RX_BD_BASE + ch_factor * sizeof(pcsca_bd_t));
-
- for (i = 0; i < N_DMA_RX_BUF; i++, ptdescr++) {
- cpc_writel(&ptdescr->next, (u32)(DMA_RX_BD_BASE +
- (ch_factor + ((i + 1) & (N_DMA_RX_BUF - 1))) * sizeof(pcsca_bd_t)));
- cpc_writel(&ptdescr->ptbuf,
- (u32)(DMA_RX_BASE + (ch_factor + i) * BD_DEF_LEN));
- }
-}
-
-static void rx_dma_buf_init(pc300_t * card, int ch)
-{
- int i;
- int ch_factor = ch * N_DMA_RX_BUF;
- volatile pcsca_bd_t __iomem *ptdescr = (card->hw.rambase
- + DMA_RX_BD_BASE + ch_factor * sizeof(pcsca_bd_t));
-
- for (i = 0; i < N_DMA_RX_BUF; i++, ptdescr++) {
- memset_io(ptdescr, 0, sizeof(pcsca_bd_t));
- cpc_writew(&ptdescr->len, 0);
- cpc_writeb(&ptdescr->status, 0);
- }
- rx_dma_buf_pt_init(card, ch);
-}
-
-static void tx_dma_buf_check(pc300_t * card, int ch)
-{
- volatile pcsca_bd_t __iomem *ptdescr;
- int i;
- u16 first_bd = card->chan[ch].tx_first_bd;
- u16 next_bd = card->chan[ch].tx_next_bd;
-
- printk("#CH%d: f_bd = %d(0x%08zx), n_bd = %d(0x%08zx)\n", ch,
- first_bd, TX_BD_ADDR(ch, first_bd),
- next_bd, TX_BD_ADDR(ch, next_bd));
- for (i = first_bd,
- ptdescr = (card->hw.rambase + TX_BD_ADDR(ch, first_bd));
- i != ((next_bd + 1) & (N_DMA_TX_BUF - 1));
- i = (i + 1) & (N_DMA_TX_BUF - 1),
- ptdescr = (card->hw.rambase + TX_BD_ADDR(ch, i))) {
- printk("\n CH%d TX%d: next=0x%x, ptbuf=0x%x, ST=0x%x, len=%d",
- ch, i, cpc_readl(&ptdescr->next),
- cpc_readl(&ptdescr->ptbuf),
- cpc_readb(&ptdescr->status), cpc_readw(&ptdescr->len));
- }
- printk("\n");
-}
-
-#ifdef PC300_DEBUG_OTHER
-/* Show all TX buffer descriptors */
-static void tx1_dma_buf_check(pc300_t * card, int ch)
-{
- volatile pcsca_bd_t __iomem *ptdescr;
- int i;
- u16 first_bd = card->chan[ch].tx_first_bd;
- u16 next_bd = card->chan[ch].tx_next_bd;
- u32 scabase = card->hw.scabase;
-
- printk ("\nnfree_tx_bd = %d\n", card->chan[ch].nfree_tx_bd);
- printk("#CH%d: f_bd = %d(0x%08x), n_bd = %d(0x%08x)\n", ch,
- first_bd, TX_BD_ADDR(ch, first_bd),
- next_bd, TX_BD_ADDR(ch, next_bd));
- printk("TX_CDA=0x%08x, TX_EDA=0x%08x\n",
- cpc_readl(scabase + DTX_REG(CDAL, ch)),
- cpc_readl(scabase + DTX_REG(EDAL, ch)));
- for (i = 0; i < N_DMA_TX_BUF; i++) {
- ptdescr = (card->hw.rambase + TX_BD_ADDR(ch, i));
- printk("\n CH%d TX%d: next=0x%x, ptbuf=0x%x, ST=0x%x, len=%d",
- ch, i, cpc_readl(&ptdescr->next),
- cpc_readl(&ptdescr->ptbuf),
- cpc_readb(&ptdescr->status), cpc_readw(&ptdescr->len));
- }
- printk("\n");
-}
-#endif
-
-static void rx_dma_buf_check(pc300_t * card, int ch)
-{
- volatile pcsca_bd_t __iomem *ptdescr;
- int i;
- u16 first_bd = card->chan[ch].rx_first_bd;
- u16 last_bd = card->chan[ch].rx_last_bd;
- int ch_factor;
-
- ch_factor = ch * N_DMA_RX_BUF;
- printk("#CH%d: f_bd = %d, l_bd = %d\n", ch, first_bd, last_bd);
- for (i = 0, ptdescr = (card->hw.rambase +
- DMA_RX_BD_BASE + ch_factor * sizeof(pcsca_bd_t));
- i < N_DMA_RX_BUF; i++, ptdescr++) {
- if (cpc_readb(&ptdescr->status) & DST_OSB)
- printk ("\n CH%d RX%d: next=0x%x, ptbuf=0x%x, ST=0x%x, len=%d",
- ch, i, cpc_readl(&ptdescr->next),
- cpc_readl(&ptdescr->ptbuf),
- cpc_readb(&ptdescr->status),
- cpc_readw(&ptdescr->len));
- }
- printk("\n");
-}
-
-static int dma_get_rx_frame_size(pc300_t * card, int ch)
-{
- volatile pcsca_bd_t __iomem *ptdescr;
- u16 first_bd = card->chan[ch].rx_first_bd;
- int rcvd = 0;
- volatile u8 status;
-
- ptdescr = (card->hw.rambase + RX_BD_ADDR(ch, first_bd));
- while ((status = cpc_readb(&ptdescr->status)) & DST_OSB) {
- rcvd += cpc_readw(&ptdescr->len);
- first_bd = (first_bd + 1) & (N_DMA_RX_BUF - 1);
- if ((status & DST_EOM) || (first_bd == card->chan[ch].rx_last_bd)) {
- /* Return the size of a good frame or incomplete bad frame
- * (dma_buf_read will clean the buffer descriptors in this case). */
- return rcvd;
- }
- ptdescr = (card->hw.rambase + cpc_readl(&ptdescr->next));
- }
- return -1;
-}
-
-/*
- * dma_buf_write: writes a frame to the Tx DMA buffers
- * NOTE: this function writes one frame at a time.
- */
-static int dma_buf_write(pc300_t *card, int ch, u8 *ptdata, int len)
-{
- int i, nchar;
- volatile pcsca_bd_t __iomem *ptdescr;
- int tosend = len;
- u8 nbuf = ((len - 1) / BD_DEF_LEN) + 1;
-
- if (nbuf >= card->chan[ch].nfree_tx_bd) {
- return -ENOMEM;
- }
-
- for (i = 0; i < nbuf; i++) {
- ptdescr = (card->hw.rambase +
- TX_BD_ADDR(ch, card->chan[ch].tx_next_bd));
- nchar = cpc_min(BD_DEF_LEN, tosend);
- if (cpc_readb(&ptdescr->status) & DST_OSB) {
- memcpy_toio((card->hw.rambase + cpc_readl(&ptdescr->ptbuf)),
- &ptdata[len - tosend], nchar);
- cpc_writew(&ptdescr->len, nchar);
- card->chan[ch].nfree_tx_bd--;
- if ((i + 1) == nbuf) {
- /* This must be the last BD to be used */
- cpc_writeb(&ptdescr->status, DST_EOM);
- } else {
- cpc_writeb(&ptdescr->status, 0);
- }
- } else {
- return -ENOMEM;
- }
- tosend -= nchar;
- card->chan[ch].tx_next_bd =
- (card->chan[ch].tx_next_bd + 1) & (N_DMA_TX_BUF - 1);
- }
- /* If it gets to here, it means we have sent the whole frame */
- return 0;
-}
-
-/*
- * dma_buf_read: reads a frame from the Rx DMA buffers
- * NOTE: this function reads one frame at a time.
- */
-static int dma_buf_read(pc300_t * card, int ch, struct sk_buff *skb)
-{
- int nchar;
- pc300ch_t *chan = (pc300ch_t *) & card->chan[ch];
- volatile pcsca_bd_t __iomem *ptdescr;
- int rcvd = 0;
- volatile u8 status;
-
- ptdescr = (card->hw.rambase +
- RX_BD_ADDR(ch, chan->rx_first_bd));
- while ((status = cpc_readb(&ptdescr->status)) & DST_OSB) {
- nchar = cpc_readw(&ptdescr->len);
- if ((status & (DST_OVR | DST_CRC | DST_RBIT | DST_SHRT | DST_ABT)) ||
- (nchar > BD_DEF_LEN)) {
-
- if (nchar > BD_DEF_LEN)
- status |= DST_RBIT;
- rcvd = -status;
- /* Discard remaining descriptors used by the bad frame */
- while (chan->rx_first_bd != chan->rx_last_bd) {
- cpc_writeb(&ptdescr->status, 0);
- chan->rx_first_bd = (chan->rx_first_bd+1) & (N_DMA_RX_BUF-1);
- if (status & DST_EOM)
- break;
- ptdescr = (card->hw.rambase +
- cpc_readl(&ptdescr->next));
- status = cpc_readb(&ptdescr->status);
- }
- break;
- }
- if (nchar != 0) {
- if (skb) {
- memcpy_fromio(skb_put(skb, nchar),
- (card->hw.rambase+cpc_readl(&ptdescr->ptbuf)),nchar);
- }
- rcvd += nchar;
- }
- cpc_writeb(&ptdescr->status, 0);
- cpc_writeb(&ptdescr->len, 0);
- chan->rx_first_bd = (chan->rx_first_bd + 1) & (N_DMA_RX_BUF - 1);
-
- if (status & DST_EOM)
- break;
-
- ptdescr = (card->hw.rambase + cpc_readl(&ptdescr->next));
- }
-
- if (rcvd != 0) {
- /* Update pointer */
- chan->rx_last_bd = (chan->rx_first_bd - 1) & (N_DMA_RX_BUF - 1);
- /* Update EDA */
- cpc_writel(card->hw.scabase + DRX_REG(EDAL, ch),
- RX_BD_ADDR(ch, chan->rx_last_bd));
- }
- return rcvd;
-}
-
-static void tx_dma_stop(pc300_t * card, int ch)
-{
- void __iomem *scabase = card->hw.scabase;
- u8 drr_ena_bit = 1 << (5 + 2 * ch);
- u8 drr_rst_bit = 1 << (1 + 2 * ch);
-
- /* Disable DMA */
- cpc_writeb(scabase + DRR, drr_ena_bit);
- cpc_writeb(scabase + DRR, drr_rst_bit & ~drr_ena_bit);
-}
-
-static void rx_dma_stop(pc300_t * card, int ch)
-{
- void __iomem *scabase = card->hw.scabase;
- u8 drr_ena_bit = 1 << (4 + 2 * ch);
- u8 drr_rst_bit = 1 << (2 * ch);
-
- /* Disable DMA */
- cpc_writeb(scabase + DRR, drr_ena_bit);
- cpc_writeb(scabase + DRR, drr_rst_bit & ~drr_ena_bit);
-}
-
-static void rx_dma_start(pc300_t * card, int ch)
-{
- void __iomem *scabase = card->hw.scabase;
- pc300ch_t *chan = (pc300ch_t *) & card->chan[ch];
-
- /* Start DMA */
- cpc_writel(scabase + DRX_REG(CDAL, ch),
- RX_BD_ADDR(ch, chan->rx_first_bd));
- if (cpc_readl(scabase + DRX_REG(CDAL,ch)) !=
- RX_BD_ADDR(ch, chan->rx_first_bd)) {
- cpc_writel(scabase + DRX_REG(CDAL, ch),
- RX_BD_ADDR(ch, chan->rx_first_bd));
- }
- cpc_writel(scabase + DRX_REG(EDAL, ch),
- RX_BD_ADDR(ch, chan->rx_last_bd));
- cpc_writew(scabase + DRX_REG(BFLL, ch), BD_DEF_LEN);
- cpc_writeb(scabase + DSR_RX(ch), DSR_DE);
- if (!(cpc_readb(scabase + DSR_RX(ch)) & DSR_DE)) {
- cpc_writeb(scabase + DSR_RX(ch), DSR_DE);
- }
-}
-
-/*************************/
-/*** FALC Routines ***/
-/*************************/
-static void falc_issue_cmd(pc300_t *card, int ch, u8 cmd)
-{
- void __iomem *falcbase = card->hw.falcbase;
- unsigned long i = 0;
-
- while (cpc_readb(falcbase + F_REG(SIS, ch)) & SIS_CEC) {
- if (i++ >= PC300_FALC_MAXLOOP) {
- printk("%s: FALC command locked(cmd=0x%x).\n",
- card->chan[ch].d.name, cmd);
- break;
- }
- }
- cpc_writeb(falcbase + F_REG(CMDR, ch), cmd);
-}
-
-static void falc_intr_enable(pc300_t * card, int ch)
-{
- pc300ch_t *chan = (pc300ch_t *) & card->chan[ch];
- pc300chconf_t *conf = (pc300chconf_t *) & chan->conf;
- falc_t *pfalc = (falc_t *) & chan->falc;
- void __iomem *falcbase = card->hw.falcbase;
-
- /* Interrupt pins are open-drain */
- cpc_writeb(falcbase + F_REG(IPC, ch),
- cpc_readb(falcbase + F_REG(IPC, ch)) & ~IPC_IC0);
- /* Conters updated each second */
- cpc_writeb(falcbase + F_REG(FMR1, ch),
- cpc_readb(falcbase + F_REG(FMR1, ch)) | FMR1_ECM);
- /* Enable SEC and ES interrupts */
- cpc_writeb(falcbase + F_REG(IMR3, ch),
- cpc_readb(falcbase + F_REG(IMR3, ch)) & ~(IMR3_SEC | IMR3_ES));
- if (conf->fr_mode == PC300_FR_UNFRAMED) {
- cpc_writeb(falcbase + F_REG(IMR4, ch),
- cpc_readb(falcbase + F_REG(IMR4, ch)) & ~(IMR4_LOS));
- } else {
- cpc_writeb(falcbase + F_REG(IMR4, ch),
- cpc_readb(falcbase + F_REG(IMR4, ch)) &
- ~(IMR4_LFA | IMR4_AIS | IMR4_LOS | IMR4_SLIP));
- }
- if (conf->media == IF_IFACE_T1) {
- cpc_writeb(falcbase + F_REG(IMR3, ch),
- cpc_readb(falcbase + F_REG(IMR3, ch)) & ~IMR3_LLBSC);
- } else {
- cpc_writeb(falcbase + F_REG(IPC, ch),
- cpc_readb(falcbase + F_REG(IPC, ch)) | IPC_SCI);
- if (conf->fr_mode == PC300_FR_UNFRAMED) {
- cpc_writeb(falcbase + F_REG(IMR2, ch),
- cpc_readb(falcbase + F_REG(IMR2, ch)) & ~(IMR2_LOS));
- } else {
- cpc_writeb(falcbase + F_REG(IMR2, ch),
- cpc_readb(falcbase + F_REG(IMR2, ch)) &
- ~(IMR2_FAR | IMR2_LFA | IMR2_AIS | IMR2_LOS));
- if (pfalc->multiframe_mode) {
- cpc_writeb(falcbase + F_REG(IMR2, ch),
- cpc_readb(falcbase + F_REG(IMR2, ch)) &
- ~(IMR2_T400MS | IMR2_MFAR));
- } else {
- cpc_writeb(falcbase + F_REG(IMR2, ch),
- cpc_readb(falcbase + F_REG(IMR2, ch)) |
- IMR2_T400MS | IMR2_MFAR);
- }
- }
- }
-}
-
-static void falc_open_timeslot(pc300_t * card, int ch, int timeslot)
-{
- void __iomem *falcbase = card->hw.falcbase;
- u8 tshf = card->chan[ch].falc.offset;
-
- cpc_writeb(falcbase + F_REG((ICB1 + (timeslot - tshf) / 8), ch),
- cpc_readb(falcbase + F_REG((ICB1 + (timeslot - tshf) / 8), ch)) &
- ~(0x80 >> ((timeslot - tshf) & 0x07)));
- cpc_writeb(falcbase + F_REG((TTR1 + timeslot / 8), ch),
- cpc_readb(falcbase + F_REG((TTR1 + timeslot / 8), ch)) |
- (0x80 >> (timeslot & 0x07)));
- cpc_writeb(falcbase + F_REG((RTR1 + timeslot / 8), ch),
- cpc_readb(falcbase + F_REG((RTR1 + timeslot / 8), ch)) |
- (0x80 >> (timeslot & 0x07)));
-}
-
-static void falc_close_timeslot(pc300_t * card, int ch, int timeslot)
-{
- void __iomem *falcbase = card->hw.falcbase;
- u8 tshf = card->chan[ch].falc.offset;
-
- cpc_writeb(falcbase + F_REG((ICB1 + (timeslot - tshf) / 8), ch),
- cpc_readb(falcbase + F_REG((ICB1 + (timeslot - tshf) / 8), ch)) |
- (0x80 >> ((timeslot - tshf) & 0x07)));
- cpc_writeb(falcbase + F_REG((TTR1 + timeslot / 8), ch),
- cpc_readb(falcbase + F_REG((TTR1 + timeslot / 8), ch)) &
- ~(0x80 >> (timeslot & 0x07)));
- cpc_writeb(falcbase + F_REG((RTR1 + timeslot / 8), ch),
- cpc_readb(falcbase + F_REG((RTR1 + timeslot / 8), ch)) &
- ~(0x80 >> (timeslot & 0x07)));
-}
-
-static void falc_close_all_timeslots(pc300_t * card, int ch)
-{
- pc300ch_t *chan = (pc300ch_t *) & card->chan[ch];
- pc300chconf_t *conf = (pc300chconf_t *) & chan->conf;
- void __iomem *falcbase = card->hw.falcbase;
-
- cpc_writeb(falcbase + F_REG(ICB1, ch), 0xff);
- cpc_writeb(falcbase + F_REG(TTR1, ch), 0);
- cpc_writeb(falcbase + F_REG(RTR1, ch), 0);
- cpc_writeb(falcbase + F_REG(ICB2, ch), 0xff);
- cpc_writeb(falcbase + F_REG(TTR2, ch), 0);
- cpc_writeb(falcbase + F_REG(RTR2, ch), 0);
- cpc_writeb(falcbase + F_REG(ICB3, ch), 0xff);
- cpc_writeb(falcbase + F_REG(TTR3, ch), 0);
- cpc_writeb(falcbase + F_REG(RTR3, ch), 0);
- if (conf->media == IF_IFACE_E1) {
- cpc_writeb(falcbase + F_REG(ICB4, ch), 0xff);
- cpc_writeb(falcbase + F_REG(TTR4, ch), 0);
- cpc_writeb(falcbase + F_REG(RTR4, ch), 0);
- }
-}
-
-static void falc_open_all_timeslots(pc300_t * card, int ch)
-{
- pc300ch_t *chan = (pc300ch_t *) & card->chan[ch];
- pc300chconf_t *conf = (pc300chconf_t *) & chan->conf;
- void __iomem *falcbase = card->hw.falcbase;
-
- cpc_writeb(falcbase + F_REG(ICB1, ch), 0);
- if (conf->fr_mode == PC300_FR_UNFRAMED) {
- cpc_writeb(falcbase + F_REG(TTR1, ch), 0xff);
- cpc_writeb(falcbase + F_REG(RTR1, ch), 0xff);
- } else {
- /* Timeslot 0 is never enabled */
- cpc_writeb(falcbase + F_REG(TTR1, ch), 0x7f);
- cpc_writeb(falcbase + F_REG(RTR1, ch), 0x7f);
- }
- cpc_writeb(falcbase + F_REG(ICB2, ch), 0);
- cpc_writeb(falcbase + F_REG(TTR2, ch), 0xff);
- cpc_writeb(falcbase + F_REG(RTR2, ch), 0xff);
- cpc_writeb(falcbase + F_REG(ICB3, ch), 0);
- cpc_writeb(falcbase + F_REG(TTR3, ch), 0xff);
- cpc_writeb(falcbase + F_REG(RTR3, ch), 0xff);
- if (conf->media == IF_IFACE_E1) {
- cpc_writeb(falcbase + F_REG(ICB4, ch), 0);
- cpc_writeb(falcbase + F_REG(TTR4, ch), 0xff);
- cpc_writeb(falcbase + F_REG(RTR4, ch), 0xff);
- } else {
- cpc_writeb(falcbase + F_REG(ICB4, ch), 0xff);
- cpc_writeb(falcbase + F_REG(TTR4, ch), 0x80);
- cpc_writeb(falcbase + F_REG(RTR4, ch), 0x80);
- }
-}
-
-static void falc_init_timeslot(pc300_t * card, int ch)
-{
- pc300ch_t *chan = (pc300ch_t *) & card->chan[ch];
- pc300chconf_t *conf = (pc300chconf_t *) & chan->conf;
- falc_t *pfalc = (falc_t *) & chan->falc;
- int tslot;
-
- for (tslot = 0; tslot < pfalc->num_channels; tslot++) {
- if (conf->tslot_bitmap & (1 << tslot)) {
- // Channel enabled
- falc_open_timeslot(card, ch, tslot + 1);
- } else {
- // Channel disabled
- falc_close_timeslot(card, ch, tslot + 1);
- }
- }
-}
-
-static void falc_enable_comm(pc300_t * card, int ch)
-{
- pc300ch_t *chan = (pc300ch_t *) & card->chan[ch];
- falc_t *pfalc = (falc_t *) & chan->falc;
-
- if (pfalc->full_bandwidth) {
- falc_open_all_timeslots(card, ch);
- } else {
- falc_init_timeslot(card, ch);
- }
- // CTS/DCD ON
- cpc_writeb(card->hw.falcbase + card->hw.cpld_reg1,
- cpc_readb(card->hw.falcbase + card->hw.cpld_reg1) &
- ~((CPLD_REG1_FALC_DCD | CPLD_REG1_FALC_CTS) << (2 * ch)));
-}
-
-static void falc_disable_comm(pc300_t * card, int ch)
-{
- pc300ch_t *chan = (pc300ch_t *) & card->chan[ch];
- falc_t *pfalc = (falc_t *) & chan->falc;
-
- if (pfalc->loop_active != 2) {
- falc_close_all_timeslots(card, ch);
- }
- // CTS/DCD OFF
- cpc_writeb(card->hw.falcbase + card->hw.cpld_reg1,
- cpc_readb(card->hw.falcbase + card->hw.cpld_reg1) |
- ((CPLD_REG1_FALC_DCD | CPLD_REG1_FALC_CTS) << (2 * ch)));
-}
-
-static void falc_init_t1(pc300_t * card, int ch)
-{
- pc300ch_t *chan = (pc300ch_t *) & card->chan[ch];
- pc300chconf_t *conf = (pc300chconf_t *) & chan->conf;
- falc_t *pfalc = (falc_t *) & chan->falc;
- void __iomem *falcbase = card->hw.falcbase;
- u8 dja = (ch ? (LIM2_DJA2 | LIM2_DJA1) : 0);
-
- /* Switch to T1 mode (PCM 24) */
- cpc_writeb(falcbase + F_REG(FMR1, ch), FMR1_PMOD);
-
- /* Wait 20 us for setup */
- udelay(20);
-
- /* Transmit Buffer Size (1 frame) */
- cpc_writeb(falcbase + F_REG(SIC1, ch), SIC1_XBS0);
-
- /* Clock mode */
- if (conf->phys_settings.clock_type == CLOCK_INT) { /* Master mode */
- cpc_writeb(falcbase + F_REG(LIM0, ch),
- cpc_readb(falcbase + F_REG(LIM0, ch)) | LIM0_MAS);
- } else { /* Slave mode */
- cpc_writeb(falcbase + F_REG(LIM0, ch),
- cpc_readb(falcbase + F_REG(LIM0, ch)) & ~LIM0_MAS);
- cpc_writeb(falcbase + F_REG(LOOP, ch),
- cpc_readb(falcbase + F_REG(LOOP, ch)) & ~LOOP_RTM);
- }
-
- cpc_writeb(falcbase + F_REG(IPC, ch), IPC_SCI);
- cpc_writeb(falcbase + F_REG(FMR0, ch),
- cpc_readb(falcbase + F_REG(FMR0, ch)) &
- ~(FMR0_XC0 | FMR0_XC1 | FMR0_RC0 | FMR0_RC1));
-
- switch (conf->lcode) {
- case PC300_LC_AMI:
- cpc_writeb(falcbase + F_REG(FMR0, ch),
- cpc_readb(falcbase + F_REG(FMR0, ch)) |
- FMR0_XC1 | FMR0_RC1);
- /* Clear Channel register to ON for all channels */
- cpc_writeb(falcbase + F_REG(CCB1, ch), 0xff);
- cpc_writeb(falcbase + F_REG(CCB2, ch), 0xff);
- cpc_writeb(falcbase + F_REG(CCB3, ch), 0xff);
- break;
-
- case PC300_LC_B8ZS:
- cpc_writeb(falcbase + F_REG(FMR0, ch),
- cpc_readb(falcbase + F_REG(FMR0, ch)) |
- FMR0_XC0 | FMR0_XC1 | FMR0_RC0 | FMR0_RC1);
- break;
-
- case PC300_LC_NRZ:
- cpc_writeb(falcbase + F_REG(FMR0, ch),
- cpc_readb(falcbase + F_REG(FMR0, ch)) | 0x00);
- break;
- }
-
- cpc_writeb(falcbase + F_REG(LIM0, ch),
- cpc_readb(falcbase + F_REG(LIM0, ch)) | LIM0_ELOS);
- cpc_writeb(falcbase + F_REG(LIM0, ch),
- cpc_readb(falcbase + F_REG(LIM0, ch)) & ~(LIM0_SCL1 | LIM0_SCL0));
- /* Set interface mode to 2 MBPS */
- cpc_writeb(falcbase + F_REG(FMR1, ch),
- cpc_readb(falcbase + F_REG(FMR1, ch)) | FMR1_IMOD);
-
- switch (conf->fr_mode) {
- case PC300_FR_ESF:
- pfalc->multiframe_mode = 0;
- cpc_writeb(falcbase + F_REG(FMR4, ch),
- cpc_readb(falcbase + F_REG(FMR4, ch)) | FMR4_FM1);
- cpc_writeb(falcbase + F_REG(FMR1, ch),
- cpc_readb(falcbase + F_REG(FMR1, ch)) |
- FMR1_CRC | FMR1_EDL);
- cpc_writeb(falcbase + F_REG(XDL1, ch), 0);
- cpc_writeb(falcbase + F_REG(XDL2, ch), 0);
- cpc_writeb(falcbase + F_REG(XDL3, ch), 0);
- cpc_writeb(falcbase + F_REG(FMR0, ch),
- cpc_readb(falcbase + F_REG(FMR0, ch)) & ~FMR0_SRAF);
- cpc_writeb(falcbase + F_REG(FMR2, ch),
- cpc_readb(falcbase + F_REG(FMR2,ch)) | FMR2_MCSP | FMR2_SSP);
- break;
-
- case PC300_FR_D4:
- pfalc->multiframe_mode = 1;
- cpc_writeb(falcbase + F_REG(FMR4, ch),
- cpc_readb(falcbase + F_REG(FMR4, ch)) &
- ~(FMR4_FM1 | FMR4_FM0));
- cpc_writeb(falcbase + F_REG(FMR0, ch),
- cpc_readb(falcbase + F_REG(FMR0, ch)) | FMR0_SRAF);
- cpc_writeb(falcbase + F_REG(FMR2, ch),
- cpc_readb(falcbase + F_REG(FMR2, ch)) & ~FMR2_SSP);
- break;
- }
-
- /* Enable Automatic Resynchronization */
- cpc_writeb(falcbase + F_REG(FMR4, ch),
- cpc_readb(falcbase + F_REG(FMR4, ch)) | FMR4_AUTO);
-
- /* Transmit Automatic Remote Alarm */
- cpc_writeb(falcbase + F_REG(FMR2, ch),
- cpc_readb(falcbase + F_REG(FMR2, ch)) | FMR2_AXRA);
-
- /* Channel translation mode 1 : one to one */
- cpc_writeb(falcbase + F_REG(FMR1, ch),
- cpc_readb(falcbase + F_REG(FMR1, ch)) | FMR1_CTM);
-
- /* No signaling */
- cpc_writeb(falcbase + F_REG(FMR1, ch),
- cpc_readb(falcbase + F_REG(FMR1, ch)) & ~FMR1_SIGM);
- cpc_writeb(falcbase + F_REG(FMR5, ch),
- cpc_readb(falcbase + F_REG(FMR5, ch)) &
- ~(FMR5_EIBR | FMR5_SRS));
- cpc_writeb(falcbase + F_REG(CCR1, ch), 0);
-
- cpc_writeb(falcbase + F_REG(LIM1, ch),
- cpc_readb(falcbase + F_REG(LIM1, ch)) | LIM1_RIL0 | LIM1_RIL1);
-
- switch (conf->lbo) {
- /* Provides proper Line Build Out */
- case PC300_LBO_0_DB:
- cpc_writeb(falcbase + F_REG(LIM2, ch), (LIM2_LOS1 | dja));
- cpc_writeb(falcbase + F_REG(XPM0, ch), 0x5a);
- cpc_writeb(falcbase + F_REG(XPM1, ch), 0x8f);
- cpc_writeb(falcbase + F_REG(XPM2, ch), 0x20);
- break;
- case PC300_LBO_7_5_DB:
- cpc_writeb(falcbase + F_REG(LIM2, ch), (0x40 | LIM2_LOS1 | dja));
- cpc_writeb(falcbase + F_REG(XPM0, ch), 0x11);
- cpc_writeb(falcbase + F_REG(XPM1, ch), 0x02);
- cpc_writeb(falcbase + F_REG(XPM2, ch), 0x20);
- break;
- case PC300_LBO_15_DB:
- cpc_writeb(falcbase + F_REG(LIM2, ch), (0x80 | LIM2_LOS1 | dja));
- cpc_writeb(falcbase + F_REG(XPM0, ch), 0x8e);
- cpc_writeb(falcbase + F_REG(XPM1, ch), 0x01);
- cpc_writeb(falcbase + F_REG(XPM2, ch), 0x20);
- break;
- case PC300_LBO_22_5_DB:
- cpc_writeb(falcbase + F_REG(LIM2, ch), (0xc0 | LIM2_LOS1 | dja));
- cpc_writeb(falcbase + F_REG(XPM0, ch), 0x09);
- cpc_writeb(falcbase + F_REG(XPM1, ch), 0x01);
- cpc_writeb(falcbase + F_REG(XPM2, ch), 0x20);
- break;
- }
-
- /* Transmit Clock-Slot Offset */
- cpc_writeb(falcbase + F_REG(XC0, ch),
- cpc_readb(falcbase + F_REG(XC0, ch)) | 0x01);
- /* Transmit Time-slot Offset */
- cpc_writeb(falcbase + F_REG(XC1, ch), 0x3e);
- /* Receive Clock-Slot offset */
- cpc_writeb(falcbase + F_REG(RC0, ch), 0x05);
- /* Receive Time-slot offset */
- cpc_writeb(falcbase + F_REG(RC1, ch), 0x00);
-
- /* LOS Detection after 176 consecutive 0s */
- cpc_writeb(falcbase + F_REG(PCDR, ch), 0x0a);
- /* LOS Recovery after 22 ones in the time window of PCD */
- cpc_writeb(falcbase + F_REG(PCRR, ch), 0x15);
-
- cpc_writeb(falcbase + F_REG(IDLE, ch), 0x7f);
-
- if (conf->fr_mode == PC300_FR_ESF_JAPAN) {
- cpc_writeb(falcbase + F_REG(RC1, ch),
- cpc_readb(falcbase + F_REG(RC1, ch)) | 0x80);
- }
-
- falc_close_all_timeslots(card, ch);
-}
-
-static void falc_init_e1(pc300_t * card, int ch)
-{
- pc300ch_t *chan = (pc300ch_t *) & card->chan[ch];
- pc300chconf_t *conf = (pc300chconf_t *) & chan->conf;
- falc_t *pfalc = (falc_t *) & chan->falc;
- void __iomem *falcbase = card->hw.falcbase;
- u8 dja = (ch ? (LIM2_DJA2 | LIM2_DJA1) : 0);
-
- /* Switch to E1 mode (PCM 30) */
- cpc_writeb(falcbase + F_REG(FMR1, ch),
- cpc_readb(falcbase + F_REG(FMR1, ch)) & ~FMR1_PMOD);
-
- /* Clock mode */
- if (conf->phys_settings.clock_type == CLOCK_INT) { /* Master mode */
- cpc_writeb(falcbase + F_REG(LIM0, ch),
- cpc_readb(falcbase + F_REG(LIM0, ch)) | LIM0_MAS);
- } else { /* Slave mode */
- cpc_writeb(falcbase + F_REG(LIM0, ch),
- cpc_readb(falcbase + F_REG(LIM0, ch)) & ~LIM0_MAS);
- }
- cpc_writeb(falcbase + F_REG(LOOP, ch),
- cpc_readb(falcbase + F_REG(LOOP, ch)) & ~LOOP_SFM);
-
- cpc_writeb(falcbase + F_REG(IPC, ch), IPC_SCI);
- cpc_writeb(falcbase + F_REG(FMR0, ch),
- cpc_readb(falcbase + F_REG(FMR0, ch)) &
- ~(FMR0_XC0 | FMR0_XC1 | FMR0_RC0 | FMR0_RC1));
-
- switch (conf->lcode) {
- case PC300_LC_AMI:
- cpc_writeb(falcbase + F_REG(FMR0, ch),
- cpc_readb(falcbase + F_REG(FMR0, ch)) |
- FMR0_XC1 | FMR0_RC1);
- break;
-
- case PC300_LC_HDB3:
- cpc_writeb(falcbase + F_REG(FMR0, ch),
- cpc_readb(falcbase + F_REG(FMR0, ch)) |
- FMR0_XC0 | FMR0_XC1 | FMR0_RC0 | FMR0_RC1);
- break;
-
- case PC300_LC_NRZ:
- break;
- }
-
- cpc_writeb(falcbase + F_REG(LIM0, ch),
- cpc_readb(falcbase + F_REG(LIM0, ch)) & ~(LIM0_SCL1 | LIM0_SCL0));
- /* Set interface mode to 2 MBPS */
- cpc_writeb(falcbase + F_REG(FMR1, ch),
- cpc_readb(falcbase + F_REG(FMR1, ch)) | FMR1_IMOD);
-
- cpc_writeb(falcbase + F_REG(XPM0, ch), 0x18);
- cpc_writeb(falcbase + F_REG(XPM1, ch), 0x03);
- cpc_writeb(falcbase + F_REG(XPM2, ch), 0x00);
-
- switch (conf->fr_mode) {
- case PC300_FR_MF_CRC4:
- pfalc->multiframe_mode = 1;
- cpc_writeb(falcbase + F_REG(FMR1, ch),
- cpc_readb(falcbase + F_REG(FMR1, ch)) | FMR1_XFS);
- cpc_writeb(falcbase + F_REG(FMR2, ch),
- cpc_readb(falcbase + F_REG(FMR2, ch)) | FMR2_RFS1);
- cpc_writeb(falcbase + F_REG(FMR2, ch),
- cpc_readb(falcbase + F_REG(FMR2, ch)) & ~FMR2_RFS0);
- cpc_writeb(falcbase + F_REG(FMR3, ch),
- cpc_readb(falcbase + F_REG(FMR3, ch)) & ~FMR3_EXTIW);
-
- /* MultiFrame Resynchronization */
- cpc_writeb(falcbase + F_REG(FMR1, ch),
- cpc_readb(falcbase + F_REG(FMR1, ch)) | FMR1_MFCS);
-
- /* Automatic Loss of Multiframe > 914 CRC errors */
- cpc_writeb(falcbase + F_REG(FMR2, ch),
- cpc_readb(falcbase + F_REG(FMR2, ch)) | FMR2_ALMF);
-
- /* S1 and SI1/SI2 spare Bits set to 1 */
- cpc_writeb(falcbase + F_REG(XSP, ch),
- cpc_readb(falcbase + F_REG(XSP, ch)) & ~XSP_AXS);
- cpc_writeb(falcbase + F_REG(XSP, ch),
- cpc_readb(falcbase + F_REG(XSP, ch)) | XSP_EBP);
- cpc_writeb(falcbase + F_REG(XSP, ch),
- cpc_readb(falcbase + F_REG(XSP, ch)) | XSP_XS13 | XSP_XS15);
-
- /* Automatic Force Resynchronization */
- cpc_writeb(falcbase + F_REG(FMR1, ch),
- cpc_readb(falcbase + F_REG(FMR1, ch)) | FMR1_AFR);
-
- /* Transmit Automatic Remote Alarm */
- cpc_writeb(falcbase + F_REG(FMR2, ch),
- cpc_readb(falcbase + F_REG(FMR2, ch)) | FMR2_AXRA);
-
- /* Transmit Spare Bits for National Use (Y, Sn, Sa) */
- cpc_writeb(falcbase + F_REG(XSW, ch),
- cpc_readb(falcbase + F_REG(XSW, ch)) |
- XSW_XY0 | XSW_XY1 | XSW_XY2 | XSW_XY3 | XSW_XY4);
- break;
-
- case PC300_FR_MF_NON_CRC4:
- case PC300_FR_D4:
- pfalc->multiframe_mode = 0;
- cpc_writeb(falcbase + F_REG(FMR1, ch),
- cpc_readb(falcbase + F_REG(FMR1, ch)) & ~FMR1_XFS);
- cpc_writeb(falcbase + F_REG(FMR2, ch),
- cpc_readb(falcbase + F_REG(FMR2, ch)) &
- ~(FMR2_RFS1 | FMR2_RFS0));
- cpc_writeb(falcbase + F_REG(XSW, ch),
- cpc_readb(falcbase + F_REG(XSW, ch)) | XSW_XSIS);
- cpc_writeb(falcbase + F_REG(XSP, ch),
- cpc_readb(falcbase + F_REG(XSP, ch)) | XSP_XSIF);
-
- /* Automatic Force Resynchronization */
- cpc_writeb(falcbase + F_REG(FMR1, ch),
- cpc_readb(falcbase + F_REG(FMR1, ch)) | FMR1_AFR);
-
- /* Transmit Automatic Remote Alarm */
- cpc_writeb(falcbase + F_REG(FMR2, ch),
- cpc_readb(falcbase + F_REG(FMR2, ch)) | FMR2_AXRA);
-
- /* Transmit Spare Bits for National Use (Y, Sn, Sa) */
- cpc_writeb(falcbase + F_REG(XSW, ch),
- cpc_readb(falcbase + F_REG(XSW, ch)) |
- XSW_XY0 | XSW_XY1 | XSW_XY2 | XSW_XY3 | XSW_XY4);
- break;
-
- case PC300_FR_UNFRAMED:
- pfalc->multiframe_mode = 0;
- cpc_writeb(falcbase + F_REG(FMR1, ch),
- cpc_readb(falcbase + F_REG(FMR1, ch)) & ~FMR1_XFS);
- cpc_writeb(falcbase + F_REG(FMR2, ch),
- cpc_readb(falcbase + F_REG(FMR2, ch)) &
- ~(FMR2_RFS1 | FMR2_RFS0));
- cpc_writeb(falcbase + F_REG(XSP, ch),
- cpc_readb(falcbase + F_REG(XSP, ch)) | XSP_TT0);
- cpc_writeb(falcbase + F_REG(XSW, ch),
- cpc_readb(falcbase + F_REG(XSW, ch)) &
- ~(XSW_XTM|XSW_XY0|XSW_XY1|XSW_XY2|XSW_XY3|XSW_XY4));
- cpc_writeb(falcbase + F_REG(TSWM, ch), 0xff);
- cpc_writeb(falcbase + F_REG(FMR2, ch),
- cpc_readb(falcbase + F_REG(FMR2, ch)) |
- (FMR2_RTM | FMR2_DAIS));
- cpc_writeb(falcbase + F_REG(FMR2, ch),
- cpc_readb(falcbase + F_REG(FMR2, ch)) & ~FMR2_AXRA);
- cpc_writeb(falcbase + F_REG(FMR1, ch),
- cpc_readb(falcbase + F_REG(FMR1, ch)) & ~FMR1_AFR);
- pfalc->sync = 1;
- cpc_writeb(falcbase + card->hw.cpld_reg2,
- cpc_readb(falcbase + card->hw.cpld_reg2) |
- (CPLD_REG2_FALC_LED2 << (2 * ch)));
- break;
- }
-
- /* No signaling */
- cpc_writeb(falcbase + F_REG(XSP, ch),
- cpc_readb(falcbase + F_REG(XSP, ch)) & ~XSP_CASEN);
- cpc_writeb(falcbase + F_REG(CCR1, ch), 0);
-
- cpc_writeb(falcbase + F_REG(LIM1, ch),
- cpc_readb(falcbase + F_REG(LIM1, ch)) | LIM1_RIL0 | LIM1_RIL1);
- cpc_writeb(falcbase + F_REG(LIM2, ch), (LIM2_LOS1 | dja));
-
- /* Transmit Clock-Slot Offset */
- cpc_writeb(falcbase + F_REG(XC0, ch),
- cpc_readb(falcbase + F_REG(XC0, ch)) | 0x01);
- /* Transmit Time-slot Offset */
- cpc_writeb(falcbase + F_REG(XC1, ch), 0x3e);
- /* Receive Clock-Slot offset */
- cpc_writeb(falcbase + F_REG(RC0, ch), 0x05);
- /* Receive Time-slot offset */
- cpc_writeb(falcbase + F_REG(RC1, ch), 0x00);
-
- /* LOS Detection after 176 consecutive 0s */
- cpc_writeb(falcbase + F_REG(PCDR, ch), 0x0a);
- /* LOS Recovery after 22 ones in the time window of PCD */
- cpc_writeb(falcbase + F_REG(PCRR, ch), 0x15);
-
- cpc_writeb(falcbase + F_REG(IDLE, ch), 0x7f);
-
- falc_close_all_timeslots(card, ch);
-}
-
-static void falc_init_hdlc(pc300_t * card, int ch)
-{
- void __iomem *falcbase = card->hw.falcbase;
- pc300ch_t *chan = (pc300ch_t *) & card->chan[ch];
- pc300chconf_t *conf = (pc300chconf_t *) & chan->conf;
-
- /* Enable transparent data transfer */
- if (conf->fr_mode == PC300_FR_UNFRAMED) {
- cpc_writeb(falcbase + F_REG(MODE, ch), 0);
- } else {
- cpc_writeb(falcbase + F_REG(MODE, ch),
- cpc_readb(falcbase + F_REG(MODE, ch)) |
- (MODE_HRAC | MODE_MDS2));
- cpc_writeb(falcbase + F_REG(RAH2, ch), 0xff);
- cpc_writeb(falcbase + F_REG(RAH1, ch), 0xff);
- cpc_writeb(falcbase + F_REG(RAL2, ch), 0xff);
- cpc_writeb(falcbase + F_REG(RAL1, ch), 0xff);
- }
-
- /* Tx/Rx reset */
- falc_issue_cmd(card, ch, CMDR_RRES | CMDR_XRES | CMDR_SRES);
-
- /* Enable interrupt sources */
- falc_intr_enable(card, ch);
-}
-
-static void te_config(pc300_t * card, int ch)
-{
- pc300ch_t *chan = (pc300ch_t *) & card->chan[ch];
- pc300chconf_t *conf = (pc300chconf_t *) & chan->conf;
- falc_t *pfalc = (falc_t *) & chan->falc;
- void __iomem *falcbase = card->hw.falcbase;
- u8 dummy;
- unsigned long flags;
-
- memset(pfalc, 0, sizeof(falc_t));
- switch (conf->media) {
- case IF_IFACE_T1:
- pfalc->num_channels = NUM_OF_T1_CHANNELS;
- pfalc->offset = 1;
- break;
- case IF_IFACE_E1:
- pfalc->num_channels = NUM_OF_E1_CHANNELS;
- pfalc->offset = 0;
- break;
- }
- if (conf->tslot_bitmap == 0xffffffffUL)
- pfalc->full_bandwidth = 1;
- else
- pfalc->full_bandwidth = 0;
-
- CPC_LOCK(card, flags);
- /* Reset the FALC chip */
- cpc_writeb(card->hw.falcbase + card->hw.cpld_reg1,
- cpc_readb(card->hw.falcbase + card->hw.cpld_reg1) |
- (CPLD_REG1_FALC_RESET << (2 * ch)));
- udelay(10000);
- cpc_writeb(card->hw.falcbase + card->hw.cpld_reg1,
- cpc_readb(card->hw.falcbase + card->hw.cpld_reg1) &
- ~(CPLD_REG1_FALC_RESET << (2 * ch)));
-
- if (conf->media == IF_IFACE_T1) {
- falc_init_t1(card, ch);
- } else {
- falc_init_e1(card, ch);
- }
- falc_init_hdlc(card, ch);
- if (conf->rx_sens == PC300_RX_SENS_SH) {
- cpc_writeb(falcbase + F_REG(LIM0, ch),
- cpc_readb(falcbase + F_REG(LIM0, ch)) & ~LIM0_EQON);
- } else {
- cpc_writeb(falcbase + F_REG(LIM0, ch),
- cpc_readb(falcbase + F_REG(LIM0, ch)) | LIM0_EQON);
- }
- cpc_writeb(card->hw.falcbase + card->hw.cpld_reg2,
- cpc_readb(card->hw.falcbase + card->hw.cpld_reg2) |
- ((CPLD_REG2_FALC_TX_CLK | CPLD_REG2_FALC_RX_CLK) << (2 * ch)));
-
- /* Clear all interrupt registers */
- dummy = cpc_readb(falcbase + F_REG(FISR0, ch)) +
- cpc_readb(falcbase + F_REG(FISR1, ch)) +
- cpc_readb(falcbase + F_REG(FISR2, ch)) +
- cpc_readb(falcbase + F_REG(FISR3, ch));
- CPC_UNLOCK(card, flags);
-}
-
-static void falc_check_status(pc300_t * card, int ch, unsigned char frs0)
-{
- pc300ch_t *chan = (pc300ch_t *) & card->chan[ch];
- pc300chconf_t *conf = (pc300chconf_t *) & chan->conf;
- falc_t *pfalc = (falc_t *) & chan->falc;
- void __iomem *falcbase = card->hw.falcbase;
-
- /* Verify LOS */
- if (frs0 & FRS0_LOS) {
- if (!pfalc->red_alarm) {
- pfalc->red_alarm = 1;
- pfalc->los++;
- if (!pfalc->blue_alarm) {
- // EVENT_FALC_ABNORMAL
- if (conf->media == IF_IFACE_T1) {
- /* Disable this interrupt as it may otherwise interfere
- * with other working boards. */
- cpc_writeb(falcbase + F_REG(IMR0, ch),
- cpc_readb(falcbase + F_REG(IMR0, ch))
- | IMR0_PDEN);
- }
- falc_disable_comm(card, ch);
- // EVENT_FALC_ABNORMAL
- }
- }
- } else {
- if (pfalc->red_alarm) {
- pfalc->red_alarm = 0;
- pfalc->losr++;
- }
- }
-
- if (conf->fr_mode != PC300_FR_UNFRAMED) {
- /* Verify AIS alarm */
- if (frs0 & FRS0_AIS) {
- if (!pfalc->blue_alarm) {
- pfalc->blue_alarm = 1;
- pfalc->ais++;
- // EVENT_AIS
- if (conf->media == IF_IFACE_T1) {
- /* Disable this interrupt as it may otherwise interfere with other working boards. */
- cpc_writeb(falcbase + F_REG(IMR0, ch),
- cpc_readb(falcbase + F_REG(IMR0, ch)) | IMR0_PDEN);
- }
- falc_disable_comm(card, ch);
- // EVENT_AIS
- }
- } else {
- pfalc->blue_alarm = 0;
- }
-
- /* Verify LFA */
- if (frs0 & FRS0_LFA) {
- if (!pfalc->loss_fa) {
- pfalc->loss_fa = 1;
- pfalc->lfa++;
- if (!pfalc->blue_alarm && !pfalc->red_alarm) {
- // EVENT_FALC_ABNORMAL
- if (conf->media == IF_IFACE_T1) {
- /* Disable this interrupt as it may otherwise
- * interfere with other working boards. */
- cpc_writeb(falcbase + F_REG(IMR0, ch),
- cpc_readb(falcbase + F_REG(IMR0, ch))
- | IMR0_PDEN);
- }
- falc_disable_comm(card, ch);
- // EVENT_FALC_ABNORMAL
- }
- }
- } else {
- if (pfalc->loss_fa) {
- pfalc->loss_fa = 0;
- pfalc->farec++;
- }
- }
-
- /* Verify LMFA */
- if (pfalc->multiframe_mode && (frs0 & FRS0_LMFA)) {
- /* D4 or CRC4 frame mode */
- if (!pfalc->loss_mfa) {
- pfalc->loss_mfa = 1;
- pfalc->lmfa++;
- if (!pfalc->blue_alarm && !pfalc->red_alarm &&
- !pfalc->loss_fa) {
- // EVENT_FALC_ABNORMAL
- if (conf->media == IF_IFACE_T1) {
- /* Disable this interrupt as it may otherwise
- * interfere with other working boards. */
- cpc_writeb(falcbase + F_REG(IMR0, ch),
- cpc_readb(falcbase + F_REG(IMR0, ch))
- | IMR0_PDEN);
- }
- falc_disable_comm(card, ch);
- // EVENT_FALC_ABNORMAL
- }
- }
- } else {
- pfalc->loss_mfa = 0;
- }
-
- /* Verify Remote Alarm */
- if (frs0 & FRS0_RRA) {
- if (!pfalc->yellow_alarm) {
- pfalc->yellow_alarm = 1;
- pfalc->rai++;
- if (pfalc->sync) {
- // EVENT_RAI
- falc_disable_comm(card, ch);
- // EVENT_RAI
- }
- }
- } else {
- pfalc->yellow_alarm = 0;
- }
- } /* if !PC300_UNFRAMED */
-
- if (pfalc->red_alarm || pfalc->loss_fa ||
- pfalc->loss_mfa || pfalc->blue_alarm) {
- if (pfalc->sync) {
- pfalc->sync = 0;
- chan->d.line_off++;
- cpc_writeb(falcbase + card->hw.cpld_reg2,
- cpc_readb(falcbase + card->hw.cpld_reg2) &
- ~(CPLD_REG2_FALC_LED2 << (2 * ch)));
- }
- } else {
- if (!pfalc->sync) {
- pfalc->sync = 1;
- chan->d.line_on++;
- cpc_writeb(falcbase + card->hw.cpld_reg2,
- cpc_readb(falcbase + card->hw.cpld_reg2) |
- (CPLD_REG2_FALC_LED2 << (2 * ch)));
- }
- }
-
- if (pfalc->sync && !pfalc->yellow_alarm) {
- if (!pfalc->active) {
- // EVENT_FALC_NORMAL
- if (pfalc->loop_active) {
- return;
- }
- if (conf->media == IF_IFACE_T1) {
- cpc_writeb(falcbase + F_REG(IMR0, ch),
- cpc_readb(falcbase + F_REG(IMR0, ch)) & ~IMR0_PDEN);
- }
- falc_enable_comm(card, ch);
- // EVENT_FALC_NORMAL
- pfalc->active = 1;
- }
- } else {
- if (pfalc->active) {
- pfalc->active = 0;
- }
- }
-}
-
-static void falc_update_stats(pc300_t * card, int ch)
-{
- pc300ch_t *chan = (pc300ch_t *) & card->chan[ch];
- pc300chconf_t *conf = (pc300chconf_t *) & chan->conf;
- falc_t *pfalc = (falc_t *) & chan->falc;
- void __iomem *falcbase = card->hw.falcbase;
- u16 counter;
-
- counter = cpc_readb(falcbase + F_REG(FECL, ch));
- counter |= cpc_readb(falcbase + F_REG(FECH, ch)) << 8;
- pfalc->fec += counter;
-
- counter = cpc_readb(falcbase + F_REG(CVCL, ch));
- counter |= cpc_readb(falcbase + F_REG(CVCH, ch)) << 8;
- pfalc->cvc += counter;
-
- counter = cpc_readb(falcbase + F_REG(CECL, ch));
- counter |= cpc_readb(falcbase + F_REG(CECH, ch)) << 8;
- pfalc->cec += counter;
-
- counter = cpc_readb(falcbase + F_REG(EBCL, ch));
- counter |= cpc_readb(falcbase + F_REG(EBCH, ch)) << 8;
- pfalc->ebc += counter;
-
- if (cpc_readb(falcbase + F_REG(LCR1, ch)) & LCR1_EPRM) {
- mdelay(10);
- counter = cpc_readb(falcbase + F_REG(BECL, ch));
- counter |= cpc_readb(falcbase + F_REG(BECH, ch)) << 8;
- pfalc->bec += counter;
-
- if (((conf->media == IF_IFACE_T1) &&
- (cpc_readb(falcbase + F_REG(FRS1, ch)) & FRS1_LLBAD) &&
- (!(cpc_readb(falcbase + F_REG(FRS1, ch)) & FRS1_PDEN))) ||
- ((conf->media == IF_IFACE_E1) &&
- (cpc_readb(falcbase + F_REG(RSP, ch)) & RSP_LLBAD))) {
- pfalc->prbs = 2;
- } else {
- pfalc->prbs = 1;
- }
- }
-}
-
-/*----------------------------------------------------------------------------
- * falc_remote_loop
- *----------------------------------------------------------------------------
- * Description: In the remote loopback mode the clock and data recovered
- * from the line inputs RL1/2 or RDIP/RDIN are routed back
- * to the line outputs XL1/2 or XDOP/XDON via the analog
- * transmitter. As in normal mode they are processed by
- * the synchronizer and then sent to the system interface.
- *----------------------------------------------------------------------------
- */
-static void falc_remote_loop(pc300_t * card, int ch, int loop_on)
-{
- pc300ch_t *chan = (pc300ch_t *) & card->chan[ch];
- pc300chconf_t *conf = (pc300chconf_t *) & chan->conf;
- falc_t *pfalc = (falc_t *) & chan->falc;
- void __iomem *falcbase = card->hw.falcbase;
-
- if (loop_on) {
- // EVENT_FALC_ABNORMAL
- if (conf->media == IF_IFACE_T1) {
- /* Disable this interrupt as it may otherwise interfere with
- * other working boards. */
- cpc_writeb(falcbase + F_REG(IMR0, ch),
- cpc_readb(falcbase + F_REG(IMR0, ch)) | IMR0_PDEN);
- }
- falc_disable_comm(card, ch);
- // EVENT_FALC_ABNORMAL
- cpc_writeb(falcbase + F_REG(LIM1, ch),
- cpc_readb(falcbase + F_REG(LIM1, ch)) | LIM1_RL);
- pfalc->loop_active = 1;
- } else {
- cpc_writeb(falcbase + F_REG(LIM1, ch),
- cpc_readb(falcbase + F_REG(LIM1, ch)) & ~LIM1_RL);
- pfalc->sync = 0;
- cpc_writeb(falcbase + card->hw.cpld_reg2,
- cpc_readb(falcbase + card->hw.cpld_reg2) &
- ~(CPLD_REG2_FALC_LED2 << (2 * ch)));
- pfalc->active = 0;
- falc_issue_cmd(card, ch, CMDR_XRES);
- pfalc->loop_active = 0;
- }
-}
-
-/*----------------------------------------------------------------------------
- * falc_local_loop
- *----------------------------------------------------------------------------
- * Description: The local loopback mode disconnects the receive lines
- * RL1/RL2 resp. RDIP/RDIN from the receiver. Instead of the
- * signals coming from the line the data provided by system
- * interface are routed through the analog receiver back to
- * the system interface. The unipolar bit stream will be
- * undisturbed transmitted on the line. Receiver and transmitter
- * coding must be identical.
- *----------------------------------------------------------------------------
- */
-static void falc_local_loop(pc300_t * card, int ch, int loop_on)
-{
- pc300ch_t *chan = (pc300ch_t *) & card->chan[ch];
- falc_t *pfalc = (falc_t *) & chan->falc;
- void __iomem *falcbase = card->hw.falcbase;
-
- if (loop_on) {
- cpc_writeb(falcbase + F_REG(LIM0, ch),
- cpc_readb(falcbase + F_REG(LIM0, ch)) | LIM0_LL);
- pfalc->loop_active = 1;
- } else {
- cpc_writeb(falcbase + F_REG(LIM0, ch),
- cpc_readb(falcbase + F_REG(LIM0, ch)) & ~LIM0_LL);
- pfalc->loop_active = 0;
- }
-}
-
-/*----------------------------------------------------------------------------
- * falc_payload_loop
- *----------------------------------------------------------------------------
- * Description: This routine allows to enable/disable payload loopback.
- * When the payload loop is activated, the received 192 bits
- * of payload data will be looped back to the transmit
- * direction. The framing bits, CRC6 and DL bits are not
- * looped. They are originated by the FALC-LH transmitter.
- *----------------------------------------------------------------------------
- */
-static void falc_payload_loop(pc300_t * card, int ch, int loop_on)
-{
- pc300ch_t *chan = (pc300ch_t *) & card->chan[ch];
- pc300chconf_t *conf = (pc300chconf_t *) & chan->conf;
- falc_t *pfalc = (falc_t *) & chan->falc;
- void __iomem *falcbase = card->hw.falcbase;
-
- if (loop_on) {
- // EVENT_FALC_ABNORMAL
- if (conf->media == IF_IFACE_T1) {
- /* Disable this interrupt as it may otherwise interfere with
- * other working boards. */
- cpc_writeb(falcbase + F_REG(IMR0, ch),
- cpc_readb(falcbase + F_REG(IMR0, ch)) | IMR0_PDEN);
- }
- falc_disable_comm(card, ch);
- // EVENT_FALC_ABNORMAL
- cpc_writeb(falcbase + F_REG(FMR2, ch),
- cpc_readb(falcbase + F_REG(FMR2, ch)) | FMR2_PLB);
- if (conf->media == IF_IFACE_T1) {
- cpc_writeb(falcbase + F_REG(FMR4, ch),
- cpc_readb(falcbase + F_REG(FMR4, ch)) | FMR4_TM);
- } else {
- cpc_writeb(falcbase + F_REG(FMR5, ch),
- cpc_readb(falcbase + F_REG(FMR5, ch)) | XSP_TT0);
- }
- falc_open_all_timeslots(card, ch);
- pfalc->loop_active = 2;
- } else {
- cpc_writeb(falcbase + F_REG(FMR2, ch),
- cpc_readb(falcbase + F_REG(FMR2, ch)) & ~FMR2_PLB);
- if (conf->media == IF_IFACE_T1) {
- cpc_writeb(falcbase + F_REG(FMR4, ch),
- cpc_readb(falcbase + F_REG(FMR4, ch)) & ~FMR4_TM);
- } else {
- cpc_writeb(falcbase + F_REG(FMR5, ch),
- cpc_readb(falcbase + F_REG(FMR5, ch)) & ~XSP_TT0);
- }
- pfalc->sync = 0;
- cpc_writeb(falcbase + card->hw.cpld_reg2,
- cpc_readb(falcbase + card->hw.cpld_reg2) &
- ~(CPLD_REG2_FALC_LED2 << (2 * ch)));
- pfalc->active = 0;
- falc_issue_cmd(card, ch, CMDR_XRES);
- pfalc->loop_active = 0;
- }
-}
-
-/*----------------------------------------------------------------------------
- * turn_off_xlu
- *----------------------------------------------------------------------------
- * Description: Turns XLU bit off in the proper register
- *----------------------------------------------------------------------------
- */
-static void turn_off_xlu(pc300_t * card, int ch)
-{
- pc300ch_t *chan = (pc300ch_t *) & card->chan[ch];
- pc300chconf_t *conf = (pc300chconf_t *) & chan->conf;
- void __iomem *falcbase = card->hw.falcbase;
-
- if (conf->media == IF_IFACE_T1) {
- cpc_writeb(falcbase + F_REG(FMR5, ch),
- cpc_readb(falcbase + F_REG(FMR5, ch)) & ~FMR5_XLU);
- } else {
- cpc_writeb(falcbase + F_REG(FMR3, ch),
- cpc_readb(falcbase + F_REG(FMR3, ch)) & ~FMR3_XLU);
- }
-}
-
-/*----------------------------------------------------------------------------
- * turn_off_xld
- *----------------------------------------------------------------------------
- * Description: Turns XLD bit off in the proper register
- *----------------------------------------------------------------------------
- */
-static void turn_off_xld(pc300_t * card, int ch)
-{
- pc300ch_t *chan = (pc300ch_t *) & card->chan[ch];
- pc300chconf_t *conf = (pc300chconf_t *) & chan->conf;
- void __iomem *falcbase = card->hw.falcbase;
-
- if (conf->media == IF_IFACE_T1) {
- cpc_writeb(falcbase + F_REG(FMR5, ch),
- cpc_readb(falcbase + F_REG(FMR5, ch)) & ~FMR5_XLD);
- } else {
- cpc_writeb(falcbase + F_REG(FMR3, ch),
- cpc_readb(falcbase + F_REG(FMR3, ch)) & ~FMR3_XLD);
- }
-}
-
-/*----------------------------------------------------------------------------
- * falc_generate_loop_up_code
- *----------------------------------------------------------------------------
- * Description: This routine writes the proper FALC chip register in order
- * to generate a LOOP activation code over a T1/E1 line.
- *----------------------------------------------------------------------------
- */
-static void falc_generate_loop_up_code(pc300_t * card, int ch)
-{
- pc300ch_t *chan = (pc300ch_t *) & card->chan[ch];
- pc300chconf_t *conf = (pc300chconf_t *) & chan->conf;
- falc_t *pfalc = (falc_t *) & chan->falc;
- void __iomem *falcbase = card->hw.falcbase;
-
- if (conf->media == IF_IFACE_T1) {
- cpc_writeb(falcbase + F_REG(FMR5, ch),
- cpc_readb(falcbase + F_REG(FMR5, ch)) | FMR5_XLU);
- } else {
- cpc_writeb(falcbase + F_REG(FMR3, ch),
- cpc_readb(falcbase + F_REG(FMR3, ch)) | FMR3_XLU);
- }
- // EVENT_FALC_ABNORMAL
- if (conf->media == IF_IFACE_T1) {
- /* Disable this interrupt as it may otherwise interfere with
- * other working boards. */
- cpc_writeb(falcbase + F_REG(IMR0, ch),
- cpc_readb(falcbase + F_REG(IMR0, ch)) | IMR0_PDEN);
- }
- falc_disable_comm(card, ch);
- // EVENT_FALC_ABNORMAL
- pfalc->loop_gen = 1;
-}
-
-/*----------------------------------------------------------------------------
- * falc_generate_loop_down_code
- *----------------------------------------------------------------------------
- * Description: This routine writes the proper FALC chip register in order
- * to generate a LOOP deactivation code over a T1/E1 line.
- *----------------------------------------------------------------------------
- */
-static void falc_generate_loop_down_code(pc300_t * card, int ch)
-{
- pc300ch_t *chan = (pc300ch_t *) & card->chan[ch];
- pc300chconf_t *conf = (pc300chconf_t *) & chan->conf;
- falc_t *pfalc = (falc_t *) & chan->falc;
- void __iomem *falcbase = card->hw.falcbase;
-
- if (conf->media == IF_IFACE_T1) {
- cpc_writeb(falcbase + F_REG(FMR5, ch),
- cpc_readb(falcbase + F_REG(FMR5, ch)) | FMR5_XLD);
- } else {
- cpc_writeb(falcbase + F_REG(FMR3, ch),
- cpc_readb(falcbase + F_REG(FMR3, ch)) | FMR3_XLD);
- }
- pfalc->sync = 0;
- cpc_writeb(falcbase + card->hw.cpld_reg2,
- cpc_readb(falcbase + card->hw.cpld_reg2) &
- ~(CPLD_REG2_FALC_LED2 << (2 * ch)));
- pfalc->active = 0;
-//? falc_issue_cmd(card, ch, CMDR_XRES);
- pfalc->loop_gen = 0;
-}
-
-/*----------------------------------------------------------------------------
- * falc_pattern_test
- *----------------------------------------------------------------------------
- * Description: This routine generates a pattern code and checks
- * it on the reception side.
- *----------------------------------------------------------------------------
- */
-static void falc_pattern_test(pc300_t * card, int ch, unsigned int activate)
-{
- pc300ch_t *chan = (pc300ch_t *) & card->chan[ch];
- pc300chconf_t *conf = (pc300chconf_t *) & chan->conf;
- falc_t *pfalc = (falc_t *) & chan->falc;
- void __iomem *falcbase = card->hw.falcbase;
-
- if (activate) {
- pfalc->prbs = 1;
- pfalc->bec = 0;
- if (conf->media == IF_IFACE_T1) {
- /* Disable local loop activation/deactivation detect */
- cpc_writeb(falcbase + F_REG(IMR3, ch),
- cpc_readb(falcbase + F_REG(IMR3, ch)) | IMR3_LLBSC);
- } else {
- /* Disable local loop activation/deactivation detect */
- cpc_writeb(falcbase + F_REG(IMR1, ch),
- cpc_readb(falcbase + F_REG(IMR1, ch)) | IMR1_LLBSC);
- }
- /* Activates generation and monitoring of PRBS
- * (Pseudo Random Bit Sequence) */
- cpc_writeb(falcbase + F_REG(LCR1, ch),
- cpc_readb(falcbase + F_REG(LCR1, ch)) | LCR1_EPRM | LCR1_XPRBS);
- } else {
- pfalc->prbs = 0;
- /* Deactivates generation and monitoring of PRBS
- * (Pseudo Random Bit Sequence) */
- cpc_writeb(falcbase + F_REG(LCR1, ch),
- cpc_readb(falcbase+F_REG(LCR1,ch)) & ~(LCR1_EPRM | LCR1_XPRBS));
- if (conf->media == IF_IFACE_T1) {
- /* Enable local loop activation/deactivation detect */
- cpc_writeb(falcbase + F_REG(IMR3, ch),
- cpc_readb(falcbase + F_REG(IMR3, ch)) & ~IMR3_LLBSC);
- } else {
- /* Enable local loop activation/deactivation detect */
- cpc_writeb(falcbase + F_REG(IMR1, ch),
- cpc_readb(falcbase + F_REG(IMR1, ch)) & ~IMR1_LLBSC);
- }
- }
-}
-
-/*----------------------------------------------------------------------------
- * falc_pattern_test_error
- *----------------------------------------------------------------------------
- * Description: This routine returns the bit error counter value
- *----------------------------------------------------------------------------
- */
-static u16 falc_pattern_test_error(pc300_t * card, int ch)
-{
- pc300ch_t *chan = (pc300ch_t *) & card->chan[ch];
- falc_t *pfalc = (falc_t *) & chan->falc;
-
- return pfalc->bec;
-}
-
-/**********************************/
-/*** Net Interface Routines ***/
-/**********************************/
-
-static void
-cpc_trace(struct net_device *dev, struct sk_buff *skb_main, char rx_tx)
-{
- struct sk_buff *skb;
-
- if ((skb = dev_alloc_skb(10 + skb_main->len)) == NULL) {
- printk("%s: out of memory\n", dev->name);
- return;
- }
- skb_put(skb, 10 + skb_main->len);
-
- skb->dev = dev;
- skb->protocol = htons(ETH_P_CUST);
- skb_reset_mac_header(skb);
- skb->pkt_type = PACKET_HOST;
- skb->len = 10 + skb_main->len;
-
- skb_copy_to_linear_data(skb, dev->name, 5);
- skb->data[5] = '[';
- skb->data[6] = rx_tx;
- skb->data[7] = ']';
- skb->data[8] = ':';
- skb->data[9] = ' ';
- skb_copy_from_linear_data(skb_main, &skb->data[10], skb_main->len);
-
- netif_rx(skb);
-}
-
-static void cpc_tx_timeout(struct net_device *dev)
-{
- pc300dev_t *d = (pc300dev_t *) dev_to_hdlc(dev)->priv;
- pc300ch_t *chan = (pc300ch_t *) d->chan;
- pc300_t *card = (pc300_t *) chan->card;
- int ch = chan->channel;
- unsigned long flags;
- u8 ilar;
-
- dev->stats.tx_errors++;
- dev->stats.tx_aborted_errors++;
- CPC_LOCK(card, flags);
- if ((ilar = cpc_readb(card->hw.scabase + ILAR)) != 0) {
- printk("%s: ILAR=0x%x\n", dev->name, ilar);
- cpc_writeb(card->hw.scabase + ILAR, ilar);
- cpc_writeb(card->hw.scabase + DMER, 0x80);
- }
- if (card->hw.type == PC300_TE) {
- cpc_writeb(card->hw.falcbase + card->hw.cpld_reg2,
- cpc_readb(card->hw.falcbase + card->hw.cpld_reg2) &
- ~(CPLD_REG2_FALC_LED1 << (2 * ch)));
- }
- dev->trans_start = jiffies; /* prevent tx timeout */
- CPC_UNLOCK(card, flags);
- netif_wake_queue(dev);
-}
-
-static int cpc_queue_xmit(struct sk_buff *skb, struct net_device *dev)
-{
- pc300dev_t *d = (pc300dev_t *) dev_to_hdlc(dev)->priv;
- pc300ch_t *chan = (pc300ch_t *) d->chan;
- pc300_t *card = (pc300_t *) chan->card;
- int ch = chan->channel;
- unsigned long flags;
-#ifdef PC300_DEBUG_TX
- int i;
-#endif
-
- if (!netif_carrier_ok(dev)) {
- /* DCD must be OFF: drop packet */
- dev_kfree_skb(skb);
- dev->stats.tx_errors++;
- dev->stats.tx_carrier_errors++;
- return 0;
- } else if (cpc_readb(card->hw.scabase + M_REG(ST3, ch)) & ST3_DCD) {
- printk("%s: DCD is OFF. Going administrative down.\n", dev->name);
- dev->stats.tx_errors++;
- dev->stats.tx_carrier_errors++;
- dev_kfree_skb(skb);
- netif_carrier_off(dev);
- CPC_LOCK(card, flags);
- cpc_writeb(card->hw.scabase + M_REG(CMD, ch), CMD_TX_BUF_CLR);
- if (card->hw.type == PC300_TE) {
- cpc_writeb(card->hw.falcbase + card->hw.cpld_reg2,
- cpc_readb(card->hw.falcbase + card->hw.cpld_reg2) &
- ~(CPLD_REG2_FALC_LED1 << (2 * ch)));
- }
- CPC_UNLOCK(card, flags);
- netif_wake_queue(dev);
- return 0;
- }
-
- /* Write buffer to DMA buffers */
- if (dma_buf_write(card, ch, (u8 *)skb->data, skb->len) != 0) {
-// printk("%s: write error. Dropping TX packet.\n", dev->name);
- netif_stop_queue(dev);
- dev_kfree_skb(skb);
- dev->stats.tx_errors++;
- dev->stats.tx_dropped++;
- return 0;
- }
-#ifdef PC300_DEBUG_TX
- printk("%s T:", dev->name);
- for (i = 0; i < skb->len; i++)
- printk(" %02x", *(skb->data + i));
- printk("\n");
-#endif
-
- if (d->trace_on) {
- cpc_trace(dev, skb, 'T');
- }
-
- /* Start transmission */
- CPC_LOCK(card, flags);
- /* verify if it has more than one free descriptor */
- if (card->chan[ch].nfree_tx_bd <= 1) {
- /* don't have so stop the queue */
- netif_stop_queue(dev);
- }
- cpc_writel(card->hw.scabase + DTX_REG(EDAL, ch),
- TX_BD_ADDR(ch, chan->tx_next_bd));
- cpc_writeb(card->hw.scabase + M_REG(CMD, ch), CMD_TX_ENA);
- cpc_writeb(card->hw.scabase + DSR_TX(ch), DSR_DE);
- if (card->hw.type == PC300_TE) {
- cpc_writeb(card->hw.falcbase + card->hw.cpld_reg2,
- cpc_readb(card->hw.falcbase + card->hw.cpld_reg2) |
- (CPLD_REG2_FALC_LED1 << (2 * ch)));
- }
- CPC_UNLOCK(card, flags);
- dev_kfree_skb(skb);
-
- return 0;
-}
-
-static void cpc_net_rx(struct net_device *dev)
-{
- pc300dev_t *d = (pc300dev_t *) dev_to_hdlc(dev)->priv;
- pc300ch_t *chan = (pc300ch_t *) d->chan;
- pc300_t *card = (pc300_t *) chan->card;
- int ch = chan->channel;
-#ifdef PC300_DEBUG_RX
- int i;
-#endif
- int rxb;
- struct sk_buff *skb;
-
- while (1) {
- if ((rxb = dma_get_rx_frame_size(card, ch)) == -1)
- return;
-
- if (!netif_carrier_ok(dev)) {
- /* DCD must be OFF: drop packet */
- printk("%s : DCD is OFF - drop %d rx bytes\n", dev->name, rxb);
- skb = NULL;
- } else {
- if (rxb > (dev->mtu + 40)) { /* add headers */
- printk("%s : MTU exceeded %d\n", dev->name, rxb);
- skb = NULL;
- } else {
- skb = dev_alloc_skb(rxb);
- if (skb == NULL) {
- printk("%s: Memory squeeze!!\n", dev->name);
- return;
- }
- skb->dev = dev;
- }
- }
-
- if (((rxb = dma_buf_read(card, ch, skb)) <= 0) || (skb == NULL)) {
-#ifdef PC300_DEBUG_RX
- printk("%s: rxb = %x\n", dev->name, rxb);
-#endif
- if ((skb == NULL) && (rxb > 0)) {
- /* rxb > dev->mtu */
- dev->stats.rx_errors++;
- dev->stats.rx_length_errors++;
- continue;
- }
-
- if (rxb < 0) { /* Invalid frame */
- rxb = -rxb;
- if (rxb & DST_OVR) {
- dev->stats.rx_errors++;
- dev->stats.rx_fifo_errors++;
- }
- if (rxb & DST_CRC) {
- dev->stats.rx_errors++;
- dev->stats.rx_crc_errors++;
- }
- if (rxb & (DST_RBIT | DST_SHRT | DST_ABT)) {
- dev->stats.rx_errors++;
- dev->stats.rx_frame_errors++;
- }
- }
- if (skb) {
- dev_kfree_skb_irq(skb);
- }
- continue;
- }
-
- dev->stats.rx_bytes += rxb;
-
-#ifdef PC300_DEBUG_RX
- printk("%s R:", dev->name);
- for (i = 0; i < skb->len; i++)
- printk(" %02x", *(skb->data + i));
- printk("\n");
-#endif
- if (d->trace_on) {
- cpc_trace(dev, skb, 'R');
- }
- dev->stats.rx_packets++;
- skb->protocol = hdlc_type_trans(skb, dev);
- netif_rx(skb);
- }
-}
-
-/************************************/
-/*** PC300 Interrupt Routines ***/
-/************************************/
-static void sca_tx_intr(pc300dev_t *dev)
-{
- pc300ch_t *chan = (pc300ch_t *)dev->chan;
- pc300_t *card = (pc300_t *)chan->card;
- int ch = chan->channel;
- volatile pcsca_bd_t __iomem * ptdescr;
-
- /* Clean up descriptors from previous transmission */
- ptdescr = (card->hw.rambase +
- TX_BD_ADDR(ch,chan->tx_first_bd));
- while ((cpc_readl(card->hw.scabase + DTX_REG(CDAL,ch)) !=
- TX_BD_ADDR(ch,chan->tx_first_bd)) &&
- (cpc_readb(&ptdescr->status) & DST_OSB)) {
- dev->dev->stats.tx_packets++;
- dev->dev->stats.tx_bytes += cpc_readw(&ptdescr->len);
- cpc_writeb(&ptdescr->status, DST_OSB);
- cpc_writew(&ptdescr->len, 0);
- chan->nfree_tx_bd++;
- chan->tx_first_bd = (chan->tx_first_bd + 1) & (N_DMA_TX_BUF - 1);
- ptdescr = (card->hw.rambase + TX_BD_ADDR(ch,chan->tx_first_bd));
- }
-
-#ifdef CONFIG_PC300_MLPPP
- if (chan->conf.proto == PC300_PROTO_MLPPP) {
- cpc_tty_trigger_poll(dev);
- } else {
-#endif
- /* Tell the upper layer we are ready to transmit more packets */
- netif_wake_queue(dev->dev);
-#ifdef CONFIG_PC300_MLPPP
- }
-#endif
-}
-
-static void sca_intr(pc300_t * card)
-{
- void __iomem *scabase = card->hw.scabase;
- volatile u32 status;
- int ch;
- int intr_count = 0;
- unsigned char dsr_rx;
-
- while ((status = cpc_readl(scabase + ISR0)) != 0) {
- for (ch = 0; ch < card->hw.nchan; ch++) {
- pc300ch_t *chan = &card->chan[ch];
- pc300dev_t *d = &chan->d;
- struct net_device *dev = d->dev;
-
- spin_lock(&card->card_lock);
-
- /**** Reception ****/
- if (status & IR0_DRX((IR0_DMIA | IR0_DMIB), ch)) {
- u8 drx_stat = cpc_readb(scabase + DSR_RX(ch));
-
- /* Clear RX interrupts */
- cpc_writeb(scabase + DSR_RX(ch), drx_stat | DSR_DWE);
-
-#ifdef PC300_DEBUG_INTR
- printk ("sca_intr: RX intr chan[%d] (st=0x%08lx, dsr=0x%02x)\n",
- ch, status, drx_stat);
-#endif
- if (status & IR0_DRX(IR0_DMIA, ch)) {
- if (drx_stat & DSR_BOF) {
-#ifdef CONFIG_PC300_MLPPP
- if (chan->conf.proto == PC300_PROTO_MLPPP) {
- /* verify if driver is TTY */
- if ((cpc_readb(scabase + DSR_RX(ch)) & DSR_DE)) {
- rx_dma_stop(card, ch);
- }
- cpc_tty_receive(d);
- rx_dma_start(card, ch);
- } else
-#endif
- {
- if ((cpc_readb(scabase + DSR_RX(ch)) & DSR_DE)) {
- rx_dma_stop(card, ch);
- }
- cpc_net_rx(dev);
- /* Discard invalid frames */
- dev->stats.rx_errors++;
- dev->stats.rx_over_errors++;
- chan->rx_first_bd = 0;
- chan->rx_last_bd = N_DMA_RX_BUF - 1;
- rx_dma_start(card, ch);
- }
- }
- }
- if (status & IR0_DRX(IR0_DMIB, ch)) {
- if (drx_stat & DSR_EOM) {
- if (card->hw.type == PC300_TE) {
- cpc_writeb(card->hw.falcbase +
- card->hw.cpld_reg2,
- cpc_readb (card->hw.falcbase +
- card->hw.cpld_reg2) |
- (CPLD_REG2_FALC_LED1 << (2 * ch)));
- }
-#ifdef CONFIG_PC300_MLPPP
- if (chan->conf.proto == PC300_PROTO_MLPPP) {
- /* verify if driver is TTY */
- cpc_tty_receive(d);
- } else {
- cpc_net_rx(dev);
- }
-#else
- cpc_net_rx(dev);
-#endif
- if (card->hw.type == PC300_TE) {
- cpc_writeb(card->hw.falcbase +
- card->hw.cpld_reg2,
- cpc_readb (card->hw.falcbase +
- card->hw.cpld_reg2) &
- ~ (CPLD_REG2_FALC_LED1 << (2 * ch)));
- }
- }
- }
- if (!(dsr_rx = cpc_readb(scabase + DSR_RX(ch)) & DSR_DE)) {
-#ifdef PC300_DEBUG_INTR
- printk("%s: RX intr chan[%d] (st=0x%08lx, dsr=0x%02x, dsr2=0x%02x)\n",
- dev->name, ch, status, drx_stat, dsr_rx);
-#endif
- cpc_writeb(scabase + DSR_RX(ch), (dsr_rx | DSR_DE) & 0xfe);
- }
- }
-
- /**** Transmission ****/
- if (status & IR0_DTX((IR0_EFT | IR0_DMIA | IR0_DMIB), ch)) {
- u8 dtx_stat = cpc_readb(scabase + DSR_TX(ch));
-
- /* Clear TX interrupts */
- cpc_writeb(scabase + DSR_TX(ch), dtx_stat | DSR_DWE);
-
-#ifdef PC300_DEBUG_INTR
- printk ("sca_intr: TX intr chan[%d] (st=0x%08lx, dsr=0x%02x)\n",
- ch, status, dtx_stat);
-#endif
- if (status & IR0_DTX(IR0_EFT, ch)) {
- if (dtx_stat & DSR_UDRF) {
- if (cpc_readb (scabase + M_REG(TBN, ch)) != 0) {
- cpc_writeb(scabase + M_REG(CMD,ch), CMD_TX_BUF_CLR);
- }
- if (card->hw.type == PC300_TE) {
- cpc_writeb(card->hw.falcbase + card->hw.cpld_reg2,
- cpc_readb (card->hw.falcbase +
- card->hw.cpld_reg2) &
- ~ (CPLD_REG2_FALC_LED1 << (2 * ch)));
- }
- dev->stats.tx_errors++;
- dev->stats.tx_fifo_errors++;
- sca_tx_intr(d);
- }
- }
- if (status & IR0_DTX(IR0_DMIA, ch)) {
- if (dtx_stat & DSR_BOF) {
- }
- }
- if (status & IR0_DTX(IR0_DMIB, ch)) {
- if (dtx_stat & DSR_EOM) {
- if (card->hw.type == PC300_TE) {
- cpc_writeb(card->hw.falcbase + card->hw.cpld_reg2,
- cpc_readb (card->hw.falcbase +
- card->hw.cpld_reg2) &
- ~ (CPLD_REG2_FALC_LED1 << (2 * ch)));
- }
- sca_tx_intr(d);
- }
- }
- }
-
- /**** MSCI ****/
- if (status & IR0_M(IR0_RXINTA, ch)) {
- u8 st1 = cpc_readb(scabase + M_REG(ST1, ch));
-
- /* Clear MSCI interrupts */
- cpc_writeb(scabase + M_REG(ST1, ch), st1);
-
-#ifdef PC300_DEBUG_INTR
- printk("sca_intr: MSCI intr chan[%d] (st=0x%08lx, st1=0x%02x)\n",
- ch, status, st1);
-#endif
- if (st1 & ST1_CDCD) { /* DCD changed */
- if (cpc_readb(scabase + M_REG(ST3, ch)) & ST3_DCD) {
- printk ("%s: DCD is OFF. Going administrative down.\n",
- dev->name);
-#ifdef CONFIG_PC300_MLPPP
- if (chan->conf.proto != PC300_PROTO_MLPPP) {
- netif_carrier_off(dev);
- }
-#else
- netif_carrier_off(dev);
-
-#endif
- card->chan[ch].d.line_off++;
- } else { /* DCD = 1 */
- printk ("%s: DCD is ON. Going administrative up.\n",
- dev->name);
-#ifdef CONFIG_PC300_MLPPP
- if (chan->conf.proto != PC300_PROTO_MLPPP)
- /* verify if driver is not TTY */
-#endif
- netif_carrier_on(dev);
- card->chan[ch].d.line_on++;
- }
- }
- }
- spin_unlock(&card->card_lock);
- }
- if (++intr_count == 10)
- /* Too much work at this board. Force exit */
- break;
- }
-}
-
-static void falc_t1_loop_detection(pc300_t *card, int ch, u8 frs1)
-{
- pc300ch_t *chan = (pc300ch_t *) & card->chan[ch];
- falc_t *pfalc = (falc_t *) & chan->falc;
- void __iomem *falcbase = card->hw.falcbase;
-
- if (((cpc_readb(falcbase + F_REG(LCR1, ch)) & LCR1_XPRBS) == 0) &&
- !pfalc->loop_gen) {
- if (frs1 & FRS1_LLBDD) {
- // A Line Loop Back Deactivation signal detected
- if (pfalc->loop_active) {
- falc_remote_loop(card, ch, 0);
- }
- } else {
- if ((frs1 & FRS1_LLBAD) &&
- ((cpc_readb(falcbase + F_REG(LCR1, ch)) & LCR1_EPRM) == 0)) {
- // A Line Loop Back Activation signal detected
- if (!pfalc->loop_active) {
- falc_remote_loop(card, ch, 1);
- }
- }
- }
- }
-}
-
-static void falc_e1_loop_detection(pc300_t *card, int ch, u8 rsp)
-{
- pc300ch_t *chan = (pc300ch_t *) & card->chan[ch];
- falc_t *pfalc = (falc_t *) & chan->falc;
- void __iomem *falcbase = card->hw.falcbase;
-
- if (((cpc_readb(falcbase + F_REG(LCR1, ch)) & LCR1_XPRBS) == 0) &&
- !pfalc->loop_gen) {
- if (rsp & RSP_LLBDD) {
- // A Line Loop Back Deactivation signal detected
- if (pfalc->loop_active) {
- falc_remote_loop(card, ch, 0);
- }
- } else {
- if ((rsp & RSP_LLBAD) &&
- ((cpc_readb(falcbase + F_REG(LCR1, ch)) & LCR1_EPRM) == 0)) {
- // A Line Loop Back Activation signal detected
- if (!pfalc->loop_active) {
- falc_remote_loop(card, ch, 1);
- }
- }
- }
- }
-}
-
-static void falc_t1_intr(pc300_t * card, int ch)
-{
- pc300ch_t *chan = (pc300ch_t *) & card->chan[ch];
- falc_t *pfalc = (falc_t *) & chan->falc;
- void __iomem *falcbase = card->hw.falcbase;
- u8 isr0, isr3, gis;
- u8 dummy;
-
- while ((gis = cpc_readb(falcbase + F_REG(GIS, ch))) != 0) {
- if (gis & GIS_ISR0) {
- isr0 = cpc_readb(falcbase + F_REG(FISR0, ch));
- if (isr0 & FISR0_PDEN) {
- /* Read the bit to clear the situation */
- if (cpc_readb(falcbase + F_REG(FRS1, ch)) &
- FRS1_PDEN) {
- pfalc->pden++;
- }
- }
- }
-
- if (gis & GIS_ISR1) {
- dummy = cpc_readb(falcbase + F_REG(FISR1, ch));
- }
-
- if (gis & GIS_ISR2) {
- dummy = cpc_readb(falcbase + F_REG(FISR2, ch));
- }
-
- if (gis & GIS_ISR3) {
- isr3 = cpc_readb(falcbase + F_REG(FISR3, ch));
- if (isr3 & FISR3_SEC) {
- pfalc->sec++;
- falc_update_stats(card, ch);
- falc_check_status(card, ch,
- cpc_readb(falcbase + F_REG(FRS0, ch)));
- }
- if (isr3 & FISR3_ES) {
- pfalc->es++;
- }
- if (isr3 & FISR3_LLBSC) {
- falc_t1_loop_detection(card, ch,
- cpc_readb(falcbase + F_REG(FRS1, ch)));
- }
- }
- }
-}
-
-static void falc_e1_intr(pc300_t * card, int ch)
-{
- pc300ch_t *chan = (pc300ch_t *) & card->chan[ch];
- falc_t *pfalc = (falc_t *) & chan->falc;
- void __iomem *falcbase = card->hw.falcbase;
- u8 isr1, isr2, isr3, gis, rsp;
- u8 dummy;
-
- while ((gis = cpc_readb(falcbase + F_REG(GIS, ch))) != 0) {
- rsp = cpc_readb(falcbase + F_REG(RSP, ch));
-
- if (gis & GIS_ISR0) {
- dummy = cpc_readb(falcbase + F_REG(FISR0, ch));
- }
- if (gis & GIS_ISR1) {
- isr1 = cpc_readb(falcbase + F_REG(FISR1, ch));
- if (isr1 & FISR1_XMB) {
- if ((pfalc->xmb_cause & 2) &&
- pfalc->multiframe_mode) {
- if (cpc_readb (falcbase + F_REG(FRS0, ch)) &
- (FRS0_LOS | FRS0_AIS | FRS0_LFA)) {
- cpc_writeb(falcbase + F_REG(XSP, ch),
- cpc_readb(falcbase + F_REG(XSP, ch))
- & ~XSP_AXS);
- } else {
- cpc_writeb(falcbase + F_REG(XSP, ch),
- cpc_readb(falcbase + F_REG(XSP, ch))
- | XSP_AXS);
- }
- }
- pfalc->xmb_cause = 0;
- cpc_writeb(falcbase + F_REG(IMR1, ch),
- cpc_readb(falcbase + F_REG(IMR1, ch)) | IMR1_XMB);
- }
- if (isr1 & FISR1_LLBSC) {
- falc_e1_loop_detection(card, ch, rsp);
- }
- }
- if (gis & GIS_ISR2) {
- isr2 = cpc_readb(falcbase + F_REG(FISR2, ch));
- if (isr2 & FISR2_T400MS) {
- cpc_writeb(falcbase + F_REG(XSW, ch),
- cpc_readb(falcbase + F_REG(XSW, ch)) | XSW_XRA);
- }
- if (isr2 & FISR2_MFAR) {
- cpc_writeb(falcbase + F_REG(XSW, ch),
- cpc_readb(falcbase + F_REG(XSW, ch)) & ~XSW_XRA);
- }
- if (isr2 & (FISR2_FAR | FISR2_LFA | FISR2_AIS | FISR2_LOS)) {
- pfalc->xmb_cause |= 2;
- cpc_writeb(falcbase + F_REG(IMR1, ch),
- cpc_readb(falcbase + F_REG(IMR1, ch)) & ~IMR1_XMB);
- }
- }
- if (gis & GIS_ISR3) {
- isr3 = cpc_readb(falcbase + F_REG(FISR3, ch));
- if (isr3 & FISR3_SEC) {
- pfalc->sec++;
- falc_update_stats(card, ch);
- falc_check_status(card, ch,
- cpc_readb(falcbase + F_REG(FRS0, ch)));
- }
- if (isr3 & FISR3_ES) {
- pfalc->es++;
- }
- }
- }
-}
-
-static void falc_intr(pc300_t * card)
-{
- int ch;
-
- for (ch = 0; ch < card->hw.nchan; ch++) {
- pc300ch_t *chan = &card->chan[ch];
- pc300chconf_t *conf = (pc300chconf_t *) & chan->conf;
-
- if (conf->media == IF_IFACE_T1) {
- falc_t1_intr(card, ch);
- } else {
- falc_e1_intr(card, ch);
- }
- }
-}
-
-static irqreturn_t cpc_intr(int irq, void *dev_id)
-{
- pc300_t *card = dev_id;
- volatile u8 plx_status;
-
- if (!card) {
-#ifdef PC300_DEBUG_INTR
- printk("cpc_intr: spurious intr %d\n", irq);
-#endif
- return IRQ_NONE; /* spurious intr */
- }
-
- if (!card->hw.rambase) {
-#ifdef PC300_DEBUG_INTR
- printk("cpc_intr: spurious intr2 %d\n", irq);
-#endif
- return IRQ_NONE; /* spurious intr */
- }
-
- switch (card->hw.type) {
- case PC300_RSV:
- case PC300_X21:
- sca_intr(card);
- break;
-
- case PC300_TE:
- while ( (plx_status = (cpc_readb(card->hw.plxbase + card->hw.intctl_reg) &
- (PLX_9050_LINT1_STATUS | PLX_9050_LINT2_STATUS))) != 0) {
- if (plx_status & PLX_9050_LINT1_STATUS) { /* SCA Interrupt */
- sca_intr(card);
- }
- if (plx_status & PLX_9050_LINT2_STATUS) { /* FALC Interrupt */
- falc_intr(card);
- }
- }
- break;
- }
- return IRQ_HANDLED;
-}
-
-static void cpc_sca_status(pc300_t * card, int ch)
-{
- u8 ilar;
- void __iomem *scabase = card->hw.scabase;
- unsigned long flags;
-
- tx_dma_buf_check(card, ch);
- rx_dma_buf_check(card, ch);
- ilar = cpc_readb(scabase + ILAR);
- printk ("ILAR=0x%02x, WCRL=0x%02x, PCR=0x%02x, BTCR=0x%02x, BOLR=0x%02x\n",
- ilar, cpc_readb(scabase + WCRL), cpc_readb(scabase + PCR),
- cpc_readb(scabase + BTCR), cpc_readb(scabase + BOLR));
- printk("TX_CDA=0x%08x, TX_EDA=0x%08x\n",
- cpc_readl(scabase + DTX_REG(CDAL, ch)),
- cpc_readl(scabase + DTX_REG(EDAL, ch)));
- printk("RX_CDA=0x%08x, RX_EDA=0x%08x, BFL=0x%04x\n",
- cpc_readl(scabase + DRX_REG(CDAL, ch)),
- cpc_readl(scabase + DRX_REG(EDAL, ch)),
- cpc_readw(scabase + DRX_REG(BFLL, ch)));
- printk("DMER=0x%02x, DSR_TX=0x%02x, DSR_RX=0x%02x\n",
- cpc_readb(scabase + DMER), cpc_readb(scabase + DSR_TX(ch)),
- cpc_readb(scabase + DSR_RX(ch)));
- printk("DMR_TX=0x%02x, DMR_RX=0x%02x, DIR_TX=0x%02x, DIR_RX=0x%02x\n",
- cpc_readb(scabase + DMR_TX(ch)), cpc_readb(scabase + DMR_RX(ch)),
- cpc_readb(scabase + DIR_TX(ch)),
- cpc_readb(scabase + DIR_RX(ch)));
- printk("DCR_TX=0x%02x, DCR_RX=0x%02x, FCT_TX=0x%02x, FCT_RX=0x%02x\n",
- cpc_readb(scabase + DCR_TX(ch)), cpc_readb(scabase + DCR_RX(ch)),
- cpc_readb(scabase + FCT_TX(ch)),
- cpc_readb(scabase + FCT_RX(ch)));
- printk("MD0=0x%02x, MD1=0x%02x, MD2=0x%02x, MD3=0x%02x, IDL=0x%02x\n",
- cpc_readb(scabase + M_REG(MD0, ch)),
- cpc_readb(scabase + M_REG(MD1, ch)),
- cpc_readb(scabase + M_REG(MD2, ch)),
- cpc_readb(scabase + M_REG(MD3, ch)),
- cpc_readb(scabase + M_REG(IDL, ch)));
- printk("CMD=0x%02x, SA0=0x%02x, SA1=0x%02x, TFN=0x%02x, CTL=0x%02x\n",
- cpc_readb(scabase + M_REG(CMD, ch)),
- cpc_readb(scabase + M_REG(SA0, ch)),
- cpc_readb(scabase + M_REG(SA1, ch)),
- cpc_readb(scabase + M_REG(TFN, ch)),
- cpc_readb(scabase + M_REG(CTL, ch)));
- printk("ST0=0x%02x, ST1=0x%02x, ST2=0x%02x, ST3=0x%02x, ST4=0x%02x\n",
- cpc_readb(scabase + M_REG(ST0, ch)),
- cpc_readb(scabase + M_REG(ST1, ch)),
- cpc_readb(scabase + M_REG(ST2, ch)),
- cpc_readb(scabase + M_REG(ST3, ch)),
- cpc_readb(scabase + M_REG(ST4, ch)));
- printk ("CST0=0x%02x, CST1=0x%02x, CST2=0x%02x, CST3=0x%02x, FST=0x%02x\n",
- cpc_readb(scabase + M_REG(CST0, ch)),
- cpc_readb(scabase + M_REG(CST1, ch)),
- cpc_readb(scabase + M_REG(CST2, ch)),
- cpc_readb(scabase + M_REG(CST3, ch)),
- cpc_readb(scabase + M_REG(FST, ch)));
- printk("TRC0=0x%02x, TRC1=0x%02x, RRC=0x%02x, TBN=0x%02x, RBN=0x%02x\n",
- cpc_readb(scabase + M_REG(TRC0, ch)),
- cpc_readb(scabase + M_REG(TRC1, ch)),
- cpc_readb(scabase + M_REG(RRC, ch)),
- cpc_readb(scabase + M_REG(TBN, ch)),
- cpc_readb(scabase + M_REG(RBN, ch)));
- printk("TFS=0x%02x, TNR0=0x%02x, TNR1=0x%02x, RNR=0x%02x\n",
- cpc_readb(scabase + M_REG(TFS, ch)),
- cpc_readb(scabase + M_REG(TNR0, ch)),
- cpc_readb(scabase + M_REG(TNR1, ch)),
- cpc_readb(scabase + M_REG(RNR, ch)));
- printk("TCR=0x%02x, RCR=0x%02x, TNR1=0x%02x, RNR=0x%02x\n",
- cpc_readb(scabase + M_REG(TCR, ch)),
- cpc_readb(scabase + M_REG(RCR, ch)),
- cpc_readb(scabase + M_REG(TNR1, ch)),
- cpc_readb(scabase + M_REG(RNR, ch)));
- printk("TXS=0x%02x, RXS=0x%02x, EXS=0x%02x, TMCT=0x%02x, TMCR=0x%02x\n",
- cpc_readb(scabase + M_REG(TXS, ch)),
- cpc_readb(scabase + M_REG(RXS, ch)),
- cpc_readb(scabase + M_REG(EXS, ch)),
- cpc_readb(scabase + M_REG(TMCT, ch)),
- cpc_readb(scabase + M_REG(TMCR, ch)));
- printk("IE0=0x%02x, IE1=0x%02x, IE2=0x%02x, IE4=0x%02x, FIE=0x%02x\n",
- cpc_readb(scabase + M_REG(IE0, ch)),
- cpc_readb(scabase + M_REG(IE1, ch)),
- cpc_readb(scabase + M_REG(IE2, ch)),
- cpc_readb(scabase + M_REG(IE4, ch)),
- cpc_readb(scabase + M_REG(FIE, ch)));
- printk("IER0=0x%08x\n", cpc_readl(scabase + IER0));
-
- if (ilar != 0) {
- CPC_LOCK(card, flags);
- cpc_writeb(scabase + ILAR, ilar);
- cpc_writeb(scabase + DMER, 0x80);
- CPC_UNLOCK(card, flags);
- }
-}
-
-static void cpc_falc_status(pc300_t * card, int ch)
-{
- pc300ch_t *chan = &card->chan[ch];
- falc_t *pfalc = (falc_t *) & chan->falc;
- unsigned long flags;
-
- CPC_LOCK(card, flags);
- printk("CH%d: %s %s %d channels\n",
- ch, (pfalc->sync ? "SYNC" : ""), (pfalc->active ? "ACTIVE" : ""),
- pfalc->num_channels);
-
- printk(" pden=%d, los=%d, losr=%d, lfa=%d, farec=%d\n",
- pfalc->pden, pfalc->los, pfalc->losr, pfalc->lfa, pfalc->farec);
- printk(" lmfa=%d, ais=%d, sec=%d, es=%d, rai=%d\n",
- pfalc->lmfa, pfalc->ais, pfalc->sec, pfalc->es, pfalc->rai);
- printk(" bec=%d, fec=%d, cvc=%d, cec=%d, ebc=%d\n",
- pfalc->bec, pfalc->fec, pfalc->cvc, pfalc->cec, pfalc->ebc);
-
- printk("\n");
- printk(" STATUS: %s %s %s %s %s %s\n",
- (pfalc->red_alarm ? "RED" : ""),
- (pfalc->blue_alarm ? "BLU" : ""),
- (pfalc->yellow_alarm ? "YEL" : ""),
- (pfalc->loss_fa ? "LFA" : ""),
- (pfalc->loss_mfa ? "LMF" : ""), (pfalc->prbs ? "PRB" : ""));
- CPC_UNLOCK(card, flags);
-}
-
-static int cpc_change_mtu(struct net_device *dev, int new_mtu)
-{
- if ((new_mtu < 128) || (new_mtu > PC300_DEF_MTU))
- return -EINVAL;
- dev->mtu = new_mtu;
- return 0;
-}
-
-static int cpc_ioctl(struct net_device *dev, struct ifreq *ifr, int cmd)
-{
- pc300dev_t *d = (pc300dev_t *) dev_to_hdlc(dev)->priv;
- pc300ch_t *chan = (pc300ch_t *) d->chan;
- pc300_t *card = (pc300_t *) chan->card;
- pc300conf_t conf_aux;
- pc300chconf_t *conf = (pc300chconf_t *) & chan->conf;
- int ch = chan->channel;
- void __user *arg = ifr->ifr_data;
- struct if_settings *settings = &ifr->ifr_settings;
- void __iomem *scabase = card->hw.scabase;
-
- if (!capable(CAP_NET_ADMIN))
- return -EPERM;
-
- switch (cmd) {
- case SIOCGPC300CONF:
-#ifdef CONFIG_PC300_MLPPP
- if (conf->proto != PC300_PROTO_MLPPP) {
- conf->proto = /* FIXME hdlc->proto.id */ 0;
- }
-#else
- conf->proto = /* FIXME hdlc->proto.id */ 0;
-#endif
- memcpy(&conf_aux.conf, conf, sizeof(pc300chconf_t));
- memcpy(&conf_aux.hw, &card->hw, sizeof(pc300hw_t));
- if (!arg ||
- copy_to_user(arg, &conf_aux, sizeof(pc300conf_t)))
- return -EINVAL;
- return 0;
- case SIOCSPC300CONF:
- if (!capable(CAP_NET_ADMIN))
- return -EPERM;
- if (!arg ||
- copy_from_user(&conf_aux.conf, arg, sizeof(pc300chconf_t)))
- return -EINVAL;
- if (card->hw.cpld_id < 0x02 &&
- conf_aux.conf.fr_mode == PC300_FR_UNFRAMED) {
- /* CPLD_ID < 0x02 doesn't support Unframed E1 */
- return -EINVAL;
- }
-#ifdef CONFIG_PC300_MLPPP
- if (conf_aux.conf.proto == PC300_PROTO_MLPPP) {
- if (conf->proto != PC300_PROTO_MLPPP) {
- memcpy(conf, &conf_aux.conf, sizeof(pc300chconf_t));
- cpc_tty_init(d); /* init TTY driver */
- }
- } else {
- if (conf_aux.conf.proto == 0xffff) {
- if (conf->proto == PC300_PROTO_MLPPP){
- /* ifdown interface */
- cpc_close(dev);
- }
- } else {
- memcpy(conf, &conf_aux.conf, sizeof(pc300chconf_t));
- /* FIXME hdlc->proto.id = conf->proto; */
- }
- }
-#else
- memcpy(conf, &conf_aux.conf, sizeof(pc300chconf_t));
- /* FIXME hdlc->proto.id = conf->proto; */
-#endif
- return 0;
- case SIOCGPC300STATUS:
- cpc_sca_status(card, ch);
- return 0;
- case SIOCGPC300FALCSTATUS:
- cpc_falc_status(card, ch);
- return 0;
-
- case SIOCGPC300UTILSTATS:
- {
- if (!arg) { /* clear statistics */
- memset(&dev->stats, 0, sizeof(dev->stats));
- if (card->hw.type == PC300_TE) {
- memset(&chan->falc, 0, sizeof(falc_t));
- }
- } else {
- pc300stats_t pc300stats;
-
- memset(&pc300stats, 0, sizeof(pc300stats_t));
- pc300stats.hw_type = card->hw.type;
- pc300stats.line_on = card->chan[ch].d.line_on;
- pc300stats.line_off = card->chan[ch].d.line_off;
- memcpy(&pc300stats.gen_stats, &dev->stats,
- sizeof(dev->stats));
- if (card->hw.type == PC300_TE)
- memcpy(&pc300stats.te_stats,&chan->falc,sizeof(falc_t));
- if (copy_to_user(arg, &pc300stats, sizeof(pc300stats_t)))
- return -EFAULT;
- }
- return 0;
- }
-
- case SIOCGPC300UTILSTATUS:
- {
- struct pc300status pc300status;
-
- pc300status.hw_type = card->hw.type;
- if (card->hw.type == PC300_TE) {
- pc300status.te_status.sync = chan->falc.sync;
- pc300status.te_status.red_alarm = chan->falc.red_alarm;
- pc300status.te_status.blue_alarm = chan->falc.blue_alarm;
- pc300status.te_status.loss_fa = chan->falc.loss_fa;
- pc300status.te_status.yellow_alarm =chan->falc.yellow_alarm;
- pc300status.te_status.loss_mfa = chan->falc.loss_mfa;
- pc300status.te_status.prbs = chan->falc.prbs;
- } else {
- pc300status.gen_status.dcd =
- !(cpc_readb (scabase + M_REG(ST3, ch)) & ST3_DCD);
- pc300status.gen_status.cts =
- !(cpc_readb (scabase + M_REG(ST3, ch)) & ST3_CTS);
- pc300status.gen_status.rts =
- !(cpc_readb (scabase + M_REG(CTL, ch)) & CTL_RTS);
- pc300status.gen_status.dtr =
- !(cpc_readb (scabase + M_REG(CTL, ch)) & CTL_DTR);
- /* There is no DSR in HD64572 */
- }
- if (!arg ||
- copy_to_user(arg, &pc300status, sizeof(pc300status_t)))
- return -EINVAL;
- return 0;
- }
-
- case SIOCSPC300TRACE:
- /* Sets/resets a trace_flag for the respective device */
- if (!arg || copy_from_user(&d->trace_on, arg,sizeof(unsigned char)))
- return -EINVAL;
- return 0;
-
- case SIOCSPC300LOOPBACK:
- {
- struct pc300loopback pc300loop;
-
- /* TE boards only */
- if (card->hw.type != PC300_TE)
- return -EINVAL;
-
- if (!arg ||
- copy_from_user(&pc300loop, arg, sizeof(pc300loopback_t)))
- return -EINVAL;
- switch (pc300loop.loop_type) {
- case PC300LOCLOOP: /* Turn the local loop on/off */
- falc_local_loop(card, ch, pc300loop.loop_on);
- return 0;
-
- case PC300REMLOOP: /* Turn the remote loop on/off */
- falc_remote_loop(card, ch, pc300loop.loop_on);
- return 0;
-
- case PC300PAYLOADLOOP: /* Turn the payload loop on/off */
- falc_payload_loop(card, ch, pc300loop.loop_on);
- return 0;
-
- case PC300GENLOOPUP: /* Generate loop UP */
- if (pc300loop.loop_on) {
- falc_generate_loop_up_code (card, ch);
- } else {
- turn_off_xlu(card, ch);
- }
- return 0;
-
- case PC300GENLOOPDOWN: /* Generate loop DOWN */
- if (pc300loop.loop_on) {
- falc_generate_loop_down_code (card, ch);
- } else {
- turn_off_xld(card, ch);
- }
- return 0;
-
- default:
- return -EINVAL;
- }
- }
-
- case SIOCSPC300PATTERNTEST:
- /* Turn the pattern test on/off and show the errors counter */
- {
- struct pc300patterntst pc300patrntst;
-
- /* TE boards only */
- if (card->hw.type != PC300_TE)
- return -EINVAL;
-
- if (card->hw.cpld_id < 0x02) {
- /* CPLD_ID < 0x02 doesn't support pattern test */
- return -EINVAL;
- }
-
- if (!arg ||
- copy_from_user(&pc300patrntst,arg,sizeof(pc300patterntst_t)))
- return -EINVAL;
- if (pc300patrntst.patrntst_on == 2) {
- if (chan->falc.prbs == 0) {
- falc_pattern_test(card, ch, 1);
- }
- pc300patrntst.num_errors =
- falc_pattern_test_error(card, ch);
- if (copy_to_user(arg, &pc300patrntst,
- sizeof(pc300patterntst_t)))
- return -EINVAL;
- } else {
- falc_pattern_test(card, ch, pc300patrntst.patrntst_on);
- }
- return 0;
- }
-
- case SIOCWANDEV:
- switch (ifr->ifr_settings.type) {
- case IF_GET_IFACE:
- {
- const size_t size = sizeof(sync_serial_settings);
- ifr->ifr_settings.type = conf->media;
- if (ifr->ifr_settings.size < size) {
- /* data size wanted */
- ifr->ifr_settings.size = size;
- return -ENOBUFS;
- }
-
- if (copy_to_user(settings->ifs_ifsu.sync,
- &conf->phys_settings, size)) {
- return -EFAULT;
- }
- return 0;
- }
-
- case IF_IFACE_V35:
- case IF_IFACE_V24:
- case IF_IFACE_X21:
- {
- const size_t size = sizeof(sync_serial_settings);
-
- if (!capable(CAP_NET_ADMIN)) {
- return -EPERM;
- }
- /* incorrect data len? */
- if (ifr->ifr_settings.size != size) {
- return -ENOBUFS;
- }
-
- if (copy_from_user(&conf->phys_settings,
- settings->ifs_ifsu.sync, size)) {
- return -EFAULT;
- }
-
- if (conf->phys_settings.loopback) {
- cpc_writeb(card->hw.scabase + M_REG(MD2, ch),
- cpc_readb(card->hw.scabase + M_REG(MD2, ch)) |
- MD2_LOOP_MIR);
- }
- conf->media = ifr->ifr_settings.type;
- return 0;
- }
-
- case IF_IFACE_T1:
- case IF_IFACE_E1:
- {
- const size_t te_size = sizeof(te1_settings);
- const size_t size = sizeof(sync_serial_settings);
-
- if (!capable(CAP_NET_ADMIN)) {
- return -EPERM;
- }
-
- /* incorrect data len? */
- if (ifr->ifr_settings.size != te_size) {
- return -ENOBUFS;
- }
-
- if (copy_from_user(&conf->phys_settings,
- settings->ifs_ifsu.te1, size)) {
- return -EFAULT;
- }/* Ignoring HDLC slot_map for a while */
-
- if (conf->phys_settings.loopback) {
- cpc_writeb(card->hw.scabase + M_REG(MD2, ch),
- cpc_readb(card->hw.scabase + M_REG(MD2, ch)) |
- MD2_LOOP_MIR);
- }
- conf->media = ifr->ifr_settings.type;
- return 0;
- }
- default:
- return hdlc_ioctl(dev, ifr, cmd);
- }
-
- default:
- return hdlc_ioctl(dev, ifr, cmd);
- }
-}
-
-static int clock_rate_calc(u32 rate, u32 clock, int *br_io)
-{
- int br, tc;
- int br_pwr, error;
-
- *br_io = 0;
-
- if (rate == 0)
- return 0;
-
- for (br = 0, br_pwr = 1; br <= 9; br++, br_pwr <<= 1) {
- if ((tc = clock / br_pwr / rate) <= 0xff) {
- *br_io = br;
- break;
- }
- }
-
- if (tc <= 0xff) {
- error = ((rate - (clock / br_pwr / rate)) / rate) * 1000;
- /* Errors bigger than +/- 1% won't be tolerated */
- if (error < -10 || error > 10)
- return -1;
- else
- return tc;
- } else {
- return -1;
- }
-}
-
-static int ch_config(pc300dev_t * d)
-{
- pc300ch_t *chan = (pc300ch_t *) d->chan;
- pc300chconf_t *conf = (pc300chconf_t *) & chan->conf;
- pc300_t *card = (pc300_t *) chan->card;
- void __iomem *scabase = card->hw.scabase;
- void __iomem *plxbase = card->hw.plxbase;
- int ch = chan->channel;
- u32 clkrate = chan->conf.phys_settings.clock_rate;
- u32 clktype = chan->conf.phys_settings.clock_type;
- u16 encoding = chan->conf.proto_settings.encoding;
- u16 parity = chan->conf.proto_settings.parity;
- u8 md0, md2;
-
- /* Reset the channel */
- cpc_writeb(scabase + M_REG(CMD, ch), CMD_CH_RST);
-
- /* Configure the SCA registers */
- switch (parity) {
- case PARITY_NONE:
- md0 = MD0_BIT_SYNC;
- break;
- case PARITY_CRC16_PR0:
- md0 = MD0_CRC16_0|MD0_CRCC0|MD0_BIT_SYNC;
- break;
- case PARITY_CRC16_PR1:
- md0 = MD0_CRC16_1|MD0_CRCC0|MD0_BIT_SYNC;
- break;
- case PARITY_CRC32_PR1_CCITT:
- md0 = MD0_CRC32|MD0_CRCC0|MD0_BIT_SYNC;
- break;
- case PARITY_CRC16_PR1_CCITT:
- default:
- md0 = MD0_CRC_CCITT|MD0_CRCC0|MD0_BIT_SYNC;
- break;
- }
- switch (encoding) {
- case ENCODING_NRZI:
- md2 = MD2_F_DUPLEX|MD2_ADPLL_X8|MD2_NRZI;
- break;
- case ENCODING_FM_MARK: /* FM1 */
- md2 = MD2_F_DUPLEX|MD2_ADPLL_X8|MD2_FM|MD2_FM1;
- break;
- case ENCODING_FM_SPACE: /* FM0 */
- md2 = MD2_F_DUPLEX|MD2_ADPLL_X8|MD2_FM|MD2_FM0;
- break;
- case ENCODING_MANCHESTER: /* It's not working... */
- md2 = MD2_F_DUPLEX|MD2_ADPLL_X8|MD2_FM|MD2_MANCH;
- break;
- case ENCODING_NRZ:
- default:
- md2 = MD2_F_DUPLEX|MD2_ADPLL_X8|MD2_NRZ;
- break;
- }
- cpc_writeb(scabase + M_REG(MD0, ch), md0);
- cpc_writeb(scabase + M_REG(MD1, ch), 0);
- cpc_writeb(scabase + M_REG(MD2, ch), md2);
- cpc_writeb(scabase + M_REG(IDL, ch), 0x7e);
- cpc_writeb(scabase + M_REG(CTL, ch), CTL_URSKP | CTL_IDLC);
-
- /* Configure HW media */
- switch (card->hw.type) {
- case PC300_RSV:
- if (conf->media == IF_IFACE_V35) {
- cpc_writel((plxbase + card->hw.gpioc_reg),
- cpc_readl(plxbase + card->hw.gpioc_reg) | PC300_CHMEDIA_MASK(ch));
- } else {
- cpc_writel((plxbase + card->hw.gpioc_reg),
- cpc_readl(plxbase + card->hw.gpioc_reg) & ~PC300_CHMEDIA_MASK(ch));
- }
- break;
-
- case PC300_X21:
- break;
-
- case PC300_TE:
- te_config(card, ch);
- break;
- }
-
- switch (card->hw.type) {
- case PC300_RSV:
- case PC300_X21:
- if (clktype == CLOCK_INT || clktype == CLOCK_TXINT) {
- int tmc, br;
-
- /* Calculate the clkrate parameters */
- tmc = clock_rate_calc(clkrate, card->hw.clock, &br);
- if (tmc < 0)
- return -EIO;
- cpc_writeb(scabase + M_REG(TMCT, ch), tmc);
- cpc_writeb(scabase + M_REG(TXS, ch),
- (TXS_DTRXC | TXS_IBRG | br));
- if (clktype == CLOCK_INT) {
- cpc_writeb(scabase + M_REG(TMCR, ch), tmc);
- cpc_writeb(scabase + M_REG(RXS, ch),
- (RXS_IBRG | br));
- } else {
- cpc_writeb(scabase + M_REG(TMCR, ch), 1);
- cpc_writeb(scabase + M_REG(RXS, ch), 0);
- }
- if (card->hw.type == PC300_X21) {
- cpc_writeb(scabase + M_REG(GPO, ch), 1);
- cpc_writeb(scabase + M_REG(EXS, ch), EXS_TES1 | EXS_RES1);
- } else {
- cpc_writeb(scabase + M_REG(EXS, ch), EXS_TES1);
- }
- } else {
- cpc_writeb(scabase + M_REG(TMCT, ch), 1);
- if (clktype == CLOCK_EXT) {
- cpc_writeb(scabase + M_REG(TXS, ch),
- TXS_DTRXC);
- } else {
- cpc_writeb(scabase + M_REG(TXS, ch),
- TXS_DTRXC|TXS_RCLK);
- }
- cpc_writeb(scabase + M_REG(TMCR, ch), 1);
- cpc_writeb(scabase + M_REG(RXS, ch), 0);
- if (card->hw.type == PC300_X21) {
- cpc_writeb(scabase + M_REG(GPO, ch), 0);
- cpc_writeb(scabase + M_REG(EXS, ch), EXS_TES1 | EXS_RES1);
- } else {
- cpc_writeb(scabase + M_REG(EXS, ch), EXS_TES1);
- }
- }
- break;
-
- case PC300_TE:
- /* SCA always receives clock from the FALC chip */
- cpc_writeb(scabase + M_REG(TMCT, ch), 1);
- cpc_writeb(scabase + M_REG(TXS, ch), 0);
- cpc_writeb(scabase + M_REG(TMCR, ch), 1);
- cpc_writeb(scabase + M_REG(RXS, ch), 0);
- cpc_writeb(scabase + M_REG(EXS, ch), 0);
- break;
- }
-
- /* Enable Interrupts */
- cpc_writel(scabase + IER0,
- cpc_readl(scabase + IER0) |
- IR0_M(IR0_RXINTA, ch) |
- IR0_DRX(IR0_EFT | IR0_DMIA | IR0_DMIB, ch) |
- IR0_DTX(IR0_EFT | IR0_DMIA | IR0_DMIB, ch));
- cpc_writeb(scabase + M_REG(IE0, ch),
- cpc_readl(scabase + M_REG(IE0, ch)) | IE0_RXINTA);
- cpc_writeb(scabase + M_REG(IE1, ch),
- cpc_readl(scabase + M_REG(IE1, ch)) | IE1_CDCD);
-
- return 0;
-}
-
-static int rx_config(pc300dev_t * d)
-{
- pc300ch_t *chan = (pc300ch_t *) d->chan;
- pc300_t *card = (pc300_t *) chan->card;
- void __iomem *scabase = card->hw.scabase;
- int ch = chan->channel;
-
- cpc_writeb(scabase + DSR_RX(ch), 0);
-
- /* General RX settings */
- cpc_writeb(scabase + M_REG(RRC, ch), 0);
- cpc_writeb(scabase + M_REG(RNR, ch), 16);
-
- /* Enable reception */
- cpc_writeb(scabase + M_REG(CMD, ch), CMD_RX_CRC_INIT);
- cpc_writeb(scabase + M_REG(CMD, ch), CMD_RX_ENA);
-
- /* Initialize DMA stuff */
- chan->rx_first_bd = 0;
- chan->rx_last_bd = N_DMA_RX_BUF - 1;
- rx_dma_buf_init(card, ch);
- cpc_writeb(scabase + DCR_RX(ch), DCR_FCT_CLR);
- cpc_writeb(scabase + DMR_RX(ch), (DMR_TMOD | DMR_NF));
- cpc_writeb(scabase + DIR_RX(ch), (DIR_EOM | DIR_BOF));
-
- /* Start DMA */
- rx_dma_start(card, ch);
-
- return 0;
-}
-
-static int tx_config(pc300dev_t * d)
-{
- pc300ch_t *chan = (pc300ch_t *) d->chan;
- pc300_t *card = (pc300_t *) chan->card;
- void __iomem *scabase = card->hw.scabase;
- int ch = chan->channel;
-
- cpc_writeb(scabase + DSR_TX(ch), 0);
-
- /* General TX settings */
- cpc_writeb(scabase + M_REG(TRC0, ch), 0);
- cpc_writeb(scabase + M_REG(TFS, ch), 32);
- cpc_writeb(scabase + M_REG(TNR0, ch), 20);
- cpc_writeb(scabase + M_REG(TNR1, ch), 48);
- cpc_writeb(scabase + M_REG(TCR, ch), 8);
-
- /* Enable transmission */
- cpc_writeb(scabase + M_REG(CMD, ch), CMD_TX_CRC_INIT);
-
- /* Initialize DMA stuff */
- chan->tx_first_bd = 0;
- chan->tx_next_bd = 0;
- tx_dma_buf_init(card, ch);
- cpc_writeb(scabase + DCR_TX(ch), DCR_FCT_CLR);
- cpc_writeb(scabase + DMR_TX(ch), (DMR_TMOD | DMR_NF));
- cpc_writeb(scabase + DIR_TX(ch), (DIR_EOM | DIR_BOF | DIR_UDRF));
- cpc_writel(scabase + DTX_REG(CDAL, ch), TX_BD_ADDR(ch, chan->tx_first_bd));
- cpc_writel(scabase + DTX_REG(EDAL, ch), TX_BD_ADDR(ch, chan->tx_next_bd));
-
- return 0;
-}
-
-static int cpc_attach(struct net_device *dev, unsigned short encoding,
- unsigned short parity)
-{
- pc300dev_t *d = (pc300dev_t *)dev_to_hdlc(dev)->priv;
- pc300ch_t *chan = (pc300ch_t *)d->chan;
- pc300_t *card = (pc300_t *)chan->card;
- pc300chconf_t *conf = (pc300chconf_t *)&chan->conf;
-
- if (card->hw.type == PC300_TE) {
- if (encoding != ENCODING_NRZ && encoding != ENCODING_NRZI) {
- return -EINVAL;
- }
- } else {
- if (encoding != ENCODING_NRZ && encoding != ENCODING_NRZI &&
- encoding != ENCODING_FM_MARK && encoding != ENCODING_FM_SPACE) {
- /* Driver doesn't support ENCODING_MANCHESTER yet */
- return -EINVAL;
- }
- }
-
- if (parity != PARITY_NONE && parity != PARITY_CRC16_PR0 &&
- parity != PARITY_CRC16_PR1 && parity != PARITY_CRC32_PR1_CCITT &&
- parity != PARITY_CRC16_PR1_CCITT) {
- return -EINVAL;
- }
-
- conf->proto_settings.encoding = encoding;
- conf->proto_settings.parity = parity;
- return 0;
-}
-
-static int cpc_opench(pc300dev_t * d)
-{
- pc300ch_t *chan = (pc300ch_t *) d->chan;
- pc300_t *card = (pc300_t *) chan->card;
- int ch = chan->channel, rc;
- void __iomem *scabase = card->hw.scabase;
-
- rc = ch_config(d);
- if (rc)
- return rc;
-
- rx_config(d);
-
- tx_config(d);
-
- /* Assert RTS and DTR */
- cpc_writeb(scabase + M_REG(CTL, ch),
- cpc_readb(scabase + M_REG(CTL, ch)) & ~(CTL_RTS | CTL_DTR));
-
- return 0;
-}
-
-static void cpc_closech(pc300dev_t * d)
-{
- pc300ch_t *chan = (pc300ch_t *) d->chan;
- pc300_t *card = (pc300_t *) chan->card;
- falc_t *pfalc = (falc_t *) & chan->falc;
- int ch = chan->channel;
-
- cpc_writeb(card->hw.scabase + M_REG(CMD, ch), CMD_CH_RST);
- rx_dma_stop(card, ch);
- tx_dma_stop(card, ch);
-
- if (card->hw.type == PC300_TE) {
- memset(pfalc, 0, sizeof(falc_t));
- cpc_writeb(card->hw.falcbase + card->hw.cpld_reg2,
- cpc_readb(card->hw.falcbase + card->hw.cpld_reg2) &
- ~((CPLD_REG2_FALC_TX_CLK | CPLD_REG2_FALC_RX_CLK |
- CPLD_REG2_FALC_LED2) << (2 * ch)));
- /* Reset the FALC chip */
- cpc_writeb(card->hw.falcbase + card->hw.cpld_reg1,
- cpc_readb(card->hw.falcbase + card->hw.cpld_reg1) |
- (CPLD_REG1_FALC_RESET << (2 * ch)));
- udelay(10000);
- cpc_writeb(card->hw.falcbase + card->hw.cpld_reg1,
- cpc_readb(card->hw.falcbase + card->hw.cpld_reg1) &
- ~(CPLD_REG1_FALC_RESET << (2 * ch)));
- }
-}
-
-int cpc_open(struct net_device *dev)
-{
- pc300dev_t *d = (pc300dev_t *) dev_to_hdlc(dev)->priv;
- struct ifreq ifr;
- int result;
-
-#ifdef PC300_DEBUG_OTHER
- printk("pc300: cpc_open");
-#endif
-
- result = hdlc_open(dev);
-
- if (result)
- return result;
-
- sprintf(ifr.ifr_name, "%s", dev->name);
- result = cpc_opench(d);
- if (result)
- goto err_out;
-
- netif_start_queue(dev);
- return 0;
-
-err_out:
- hdlc_close(dev);
- return result;
-}
-
-static int cpc_close(struct net_device *dev)
-{
- pc300dev_t *d = (pc300dev_t *) dev_to_hdlc(dev)->priv;
- pc300ch_t *chan = (pc300ch_t *) d->chan;
- pc300_t *card = (pc300_t *) chan->card;
- unsigned long flags;
-
-#ifdef PC300_DEBUG_OTHER
- printk("pc300: cpc_close");
-#endif
-
- netif_stop_queue(dev);
-
- CPC_LOCK(card, flags);
- cpc_closech(d);
- CPC_UNLOCK(card, flags);
-
- hdlc_close(dev);
-
-#ifdef CONFIG_PC300_MLPPP
- if (chan->conf.proto == PC300_PROTO_MLPPP) {
- cpc_tty_unregister_service(d);
- chan->conf.proto = 0xffff;
- }
-#endif
-
- return 0;
-}
-
-static u32 detect_ram(pc300_t * card)
-{
- u32 i;
- u8 data;
- void __iomem *rambase = card->hw.rambase;
-
- card->hw.ramsize = PC300_RAMSIZE;
- /* Let's find out how much RAM is present on this board */
- for (i = 0; i < card->hw.ramsize; i++) {
- data = (u8)(i & 0xff);
- cpc_writeb(rambase + i, data);
- if (cpc_readb(rambase + i) != data) {
- break;
- }
- }
- return i;
-}
-
-static void plx_init(pc300_t * card)
-{
- struct RUNTIME_9050 __iomem *plx_ctl = card->hw.plxbase;
-
- /* Reset PLX */
- cpc_writel(&plx_ctl->init_ctrl,
- cpc_readl(&plx_ctl->init_ctrl) | 0x40000000);
- udelay(10000L);
- cpc_writel(&plx_ctl->init_ctrl,
- cpc_readl(&plx_ctl->init_ctrl) & ~0x40000000);
-
- /* Reload Config. Registers from EEPROM */
- cpc_writel(&plx_ctl->init_ctrl,
- cpc_readl(&plx_ctl->init_ctrl) | 0x20000000);
- udelay(10000L);
- cpc_writel(&plx_ctl->init_ctrl,
- cpc_readl(&plx_ctl->init_ctrl) & ~0x20000000);
-
-}
-
-static void show_version(void)
-{
- char *rcsvers, *rcsdate, *tmp;
-
- rcsvers = strchr(rcsid, ' ');
- rcsvers++;
- tmp = strchr(rcsvers, ' ');
- *tmp++ = '\0';
- rcsdate = strchr(tmp, ' ');
- rcsdate++;
- tmp = strrchr(rcsdate, ' ');
- *tmp = '\0';
- pr_info("Cyclades-PC300 driver %s %s\n", rcsvers, rcsdate);
-} /* show_version */
-
-static const struct net_device_ops cpc_netdev_ops = {
- .ndo_open = cpc_open,
- .ndo_stop = cpc_close,
- .ndo_tx_timeout = cpc_tx_timeout,
- .ndo_set_mac_address = NULL,
- .ndo_change_mtu = cpc_change_mtu,
- .ndo_do_ioctl = cpc_ioctl,
- .ndo_validate_addr = eth_validate_addr,
-};
-
-static void cpc_init_card(pc300_t * card)
-{
- int i, devcount = 0;
- static int board_nbr = 1;
-
- /* Enable interrupts on the PCI bridge */
- plx_init(card);
- cpc_writew(card->hw.plxbase + card->hw.intctl_reg,
- cpc_readw(card->hw.plxbase + card->hw.intctl_reg) | 0x0040);
-
-#ifdef USE_PCI_CLOCK
- /* Set board clock to PCI clock */
- cpc_writel(card->hw.plxbase + card->hw.gpioc_reg,
- cpc_readl(card->hw.plxbase + card->hw.gpioc_reg) | 0x00000004UL);
- card->hw.clock = PC300_PCI_CLOCK;
-#else
- /* Set board clock to internal oscillator clock */
- cpc_writel(card->hw.plxbase + card->hw.gpioc_reg,
- cpc_readl(card->hw.plxbase + card->hw.gpioc_reg) & ~0x00000004UL);
- card->hw.clock = PC300_OSC_CLOCK;
-#endif
-
- /* Detect actual on-board RAM size */
- card->hw.ramsize = detect_ram(card);
-
- /* Set Global SCA-II registers */
- cpc_writeb(card->hw.scabase + PCR, PCR_PR2);
- cpc_writeb(card->hw.scabase + BTCR, 0x10);
- cpc_writeb(card->hw.scabase + WCRL, 0);
- cpc_writeb(card->hw.scabase + DMER, 0x80);
-
- if (card->hw.type == PC300_TE) {
- u8 reg1;
-
- /* Check CPLD version */
- reg1 = cpc_readb(card->hw.falcbase + CPLD_REG1);
- cpc_writeb(card->hw.falcbase + CPLD_REG1, (reg1 + 0x5a));
- if (cpc_readb(card->hw.falcbase + CPLD_REG1) == reg1) {
- /* New CPLD */
- card->hw.cpld_id = cpc_readb(card->hw.falcbase + CPLD_ID_REG);
- card->hw.cpld_reg1 = CPLD_V2_REG1;
- card->hw.cpld_reg2 = CPLD_V2_REG2;
- } else {
- /* old CPLD */
- card->hw.cpld_id = 0;
- card->hw.cpld_reg1 = CPLD_REG1;
- card->hw.cpld_reg2 = CPLD_REG2;
- cpc_writeb(card->hw.falcbase + CPLD_REG1, reg1);
- }
-
- /* Enable the board's global clock */
- cpc_writeb(card->hw.falcbase + card->hw.cpld_reg1,
- cpc_readb(card->hw.falcbase + card->hw.cpld_reg1) |
- CPLD_REG1_GLOBAL_CLK);
-
- }
-
- for (i = 0; i < card->hw.nchan; i++) {
- pc300ch_t *chan = &card->chan[i];
- pc300dev_t *d = &chan->d;
- hdlc_device *hdlc;
- struct net_device *dev;
-
- chan->card = card;
- chan->channel = i;
- chan->conf.phys_settings.clock_rate = 0;
- chan->conf.phys_settings.clock_type = CLOCK_EXT;
- chan->conf.proto_settings.encoding = ENCODING_NRZ;
- chan->conf.proto_settings.parity = PARITY_CRC16_PR1_CCITT;
- switch (card->hw.type) {
- case PC300_TE:
- chan->conf.media = IF_IFACE_T1;
- chan->conf.lcode = PC300_LC_B8ZS;
- chan->conf.fr_mode = PC300_FR_ESF;
- chan->conf.lbo = PC300_LBO_0_DB;
- chan->conf.rx_sens = PC300_RX_SENS_SH;
- chan->conf.tslot_bitmap = 0xffffffffUL;
- break;
-
- case PC300_X21:
- chan->conf.media = IF_IFACE_X21;
- break;
-
- case PC300_RSV:
- default:
- chan->conf.media = IF_IFACE_V35;
- break;
- }
- chan->conf.proto = IF_PROTO_PPP;
- chan->tx_first_bd = 0;
- chan->tx_next_bd = 0;
- chan->rx_first_bd = 0;
- chan->rx_last_bd = N_DMA_RX_BUF - 1;
- chan->nfree_tx_bd = N_DMA_TX_BUF;
-
- d->chan = chan;
- d->trace_on = 0;
- d->line_on = 0;
- d->line_off = 0;
-
- dev = alloc_hdlcdev(d);
- if (dev == NULL)
- continue;
-
- hdlc = dev_to_hdlc(dev);
- hdlc->xmit = cpc_queue_xmit;
- hdlc->attach = cpc_attach;
- d->dev = dev;
- dev->mem_start = card->hw.ramphys;
- dev->mem_end = card->hw.ramphys + card->hw.ramsize - 1;
- dev->irq = card->hw.irq;
- dev->tx_queue_len = PC300_TX_QUEUE_LEN;
- dev->mtu = PC300_DEF_MTU;
-
- dev->netdev_ops = &cpc_netdev_ops;
- dev->watchdog_timeo = PC300_TX_TIMEOUT;
-
- if (register_hdlc_device(dev) == 0) {
- printk("%s: Cyclades-PC300/", dev->name);
- switch (card->hw.type) {
- case PC300_TE:
- if (card->hw.bus == PC300_PMC) {
- printk("TE-M");
- } else {
- printk("TE ");
- }
- break;
-
- case PC300_X21:
- printk("X21 ");
- break;
-
- case PC300_RSV:
- default:
- printk("RSV ");
- break;
- }
- printk (" #%d, %dKB of RAM at 0x%08x, IRQ%d, channel %d.\n",
- board_nbr, card->hw.ramsize / 1024,
- card->hw.ramphys, card->hw.irq, i + 1);
- devcount++;
- } else {
- printk ("Dev%d on card(0x%08x): unable to allocate i/f name.\n",
- i + 1, card->hw.ramphys);
- free_netdev(dev);
- continue;
- }
- }
- spin_lock_init(&card->card_lock);
-
- board_nbr++;
-}
-
-static int __devinit
-cpc_init_one(struct pci_dev *pdev, const struct pci_device_id *ent)
-{
- int err, eeprom_outdated = 0;
- u16 device_id;
- pc300_t *card;
-
- if ((err = pci_enable_device(pdev)) < 0)
- return err;
-
- card = kzalloc(sizeof(pc300_t), GFP_KERNEL);
- if (card == NULL) {
- printk("PC300 found at RAM 0x%016llx, "
- "but could not allocate card structure.\n",
- (unsigned long long)pci_resource_start(pdev, 3));
- err = -ENOMEM;
- goto err_disable_dev;
- }
-
- err = -ENODEV;
-
- /* read PCI configuration area */
- device_id = ent->device;
- card->hw.irq = pdev->irq;
- card->hw.iophys = pci_resource_start(pdev, 1);
- card->hw.iosize = pci_resource_len(pdev, 1);
- card->hw.scaphys = pci_resource_start(pdev, 2);
- card->hw.scasize = pci_resource_len(pdev, 2);
- card->hw.ramphys = pci_resource_start(pdev, 3);
- card->hw.alloc_ramsize = pci_resource_len(pdev, 3);
- card->hw.falcphys = pci_resource_start(pdev, 4);
- card->hw.falcsize = pci_resource_len(pdev, 4);
- card->hw.plxphys = pci_resource_start(pdev, 5);
- card->hw.plxsize = pci_resource_len(pdev, 5);
-
- switch (device_id) {
- case PCI_DEVICE_ID_PC300_RX_1:
- case PCI_DEVICE_ID_PC300_TE_1:
- case PCI_DEVICE_ID_PC300_TE_M_1:
- card->hw.nchan = 1;
- break;
-
- case PCI_DEVICE_ID_PC300_RX_2:
- case PCI_DEVICE_ID_PC300_TE_2:
- case PCI_DEVICE_ID_PC300_TE_M_2:
- default:
- card->hw.nchan = PC300_MAXCHAN;
- break;
- }
-#ifdef PC300_DEBUG_PCI
- printk("cpc (bus=0x0%x,pci_id=0x%x,", pdev->bus->number, pdev->devfn);
- printk("rev_id=%d) IRQ%d\n", pdev->revision, card->hw.irq);
- printk("cpc:found ramaddr=0x%08lx plxaddr=0x%08lx "
- "ctladdr=0x%08lx falcaddr=0x%08lx\n",
- card->hw.ramphys, card->hw.plxphys, card->hw.scaphys,
- card->hw.falcphys);
-#endif
- /* Although we don't use this I/O region, we should
- * request it from the kernel anyway, to avoid problems
- * with other drivers accessing it. */
- if (!request_region(card->hw.iophys, card->hw.iosize, "PLX Registers")) {
- /* In case we can't allocate it, warn user */
- printk("WARNING: couldn't allocate I/O region for PC300 board "
- "at 0x%08x!\n", card->hw.ramphys);
- }
-
- if (card->hw.plxphys) {
- pci_write_config_dword(pdev, PCI_BASE_ADDRESS_0, card->hw.plxphys);
- } else {
- eeprom_outdated = 1;
- card->hw.plxphys = pci_resource_start(pdev, 0);
- card->hw.plxsize = pci_resource_len(pdev, 0);
- }
-
- if (!request_mem_region(card->hw.plxphys, card->hw.plxsize,
- "PLX Registers")) {
- printk("PC300 found at RAM 0x%08x, "
- "but could not allocate PLX mem region.\n",
- card->hw.ramphys);
- goto err_release_io;
- }
- if (!request_mem_region(card->hw.ramphys, card->hw.alloc_ramsize,
- "On-board RAM")) {
- printk("PC300 found at RAM 0x%08x, "
- "but could not allocate RAM mem region.\n",
- card->hw.ramphys);
- goto err_release_plx;
- }
- if (!request_mem_region(card->hw.scaphys, card->hw.scasize,
- "SCA-II Registers")) {
- printk("PC300 found at RAM 0x%08x, "
- "but could not allocate SCA mem region.\n",
- card->hw.ramphys);
- goto err_release_ram;
- }
-
- card->hw.plxbase = ioremap(card->hw.plxphys, card->hw.plxsize);
- card->hw.rambase = ioremap(card->hw.ramphys, card->hw.alloc_ramsize);
- card->hw.scabase = ioremap(card->hw.scaphys, card->hw.scasize);
- switch (device_id) {
- case PCI_DEVICE_ID_PC300_TE_1:
- case PCI_DEVICE_ID_PC300_TE_2:
- case PCI_DEVICE_ID_PC300_TE_M_1:
- case PCI_DEVICE_ID_PC300_TE_M_2:
- request_mem_region(card->hw.falcphys, card->hw.falcsize,
- "FALC Registers");
- card->hw.falcbase = ioremap(card->hw.falcphys, card->hw.falcsize);
- break;
-
- case PCI_DEVICE_ID_PC300_RX_1:
- case PCI_DEVICE_ID_PC300_RX_2:
- default:
- card->hw.falcbase = NULL;
- break;
- }
-
-#ifdef PC300_DEBUG_PCI
- printk("cpc: relocate ramaddr=0x%08lx plxaddr=0x%08lx "
- "ctladdr=0x%08lx falcaddr=0x%08lx\n",
- card->hw.rambase, card->hw.plxbase, card->hw.scabase,
- card->hw.falcbase);
-#endif
-
- /* Set PCI drv pointer to the card structure */
- pci_set_drvdata(pdev, card);
-
- /* Set board type */
- switch (device_id) {
- case PCI_DEVICE_ID_PC300_TE_1:
- case PCI_DEVICE_ID_PC300_TE_2:
- case PCI_DEVICE_ID_PC300_TE_M_1:
- case PCI_DEVICE_ID_PC300_TE_M_2:
- card->hw.type = PC300_TE;
-
- if ((device_id == PCI_DEVICE_ID_PC300_TE_M_1) ||
- (device_id == PCI_DEVICE_ID_PC300_TE_M_2)) {
- card->hw.bus = PC300_PMC;
- /* Set PLX register offsets */
- card->hw.gpioc_reg = 0x54;
- card->hw.intctl_reg = 0x4c;
- } else {
- card->hw.bus = PC300_PCI;
- /* Set PLX register offsets */
- card->hw.gpioc_reg = 0x50;
- card->hw.intctl_reg = 0x4c;
- }
- break;
-
- case PCI_DEVICE_ID_PC300_RX_1:
- case PCI_DEVICE_ID_PC300_RX_2:
- default:
- card->hw.bus = PC300_PCI;
- /* Set PLX register offsets */
- card->hw.gpioc_reg = 0x50;
- card->hw.intctl_reg = 0x4c;
-
- if ((cpc_readl(card->hw.plxbase + card->hw.gpioc_reg) & PC300_CTYPE_MASK)) {
- card->hw.type = PC300_X21;
- } else {
- card->hw.type = PC300_RSV;
- }
- break;
- }
-
- /* Allocate IRQ */
- if (request_irq(card->hw.irq, cpc_intr, IRQF_SHARED, "Cyclades-PC300", card)) {
- printk ("PC300 found at RAM 0x%08x, but could not allocate IRQ%d.\n",
- card->hw.ramphys, card->hw.irq);
- goto err_io_unmap;
- }
-
- cpc_init_card(card);
-
- if (eeprom_outdated)
- printk("WARNING: PC300 with outdated EEPROM.\n");
- return 0;
-
-err_io_unmap:
- iounmap(card->hw.plxbase);
- iounmap(card->hw.scabase);
- iounmap(card->hw.rambase);
- if (card->hw.type == PC300_TE) {
- iounmap(card->hw.falcbase);
- release_mem_region(card->hw.falcphys, card->hw.falcsize);
- }
- release_mem_region(card->hw.scaphys, card->hw.scasize);
-err_release_ram:
- release_mem_region(card->hw.ramphys, card->hw.alloc_ramsize);
-err_release_plx:
- release_mem_region(card->hw.plxphys, card->hw.plxsize);
-err_release_io:
- release_region(card->hw.iophys, card->hw.iosize);
- kfree(card);
-err_disable_dev:
- pci_disable_device(pdev);
- return err;
-}
-
-static void __devexit cpc_remove_one(struct pci_dev *pdev)
-{
- pc300_t *card = pci_get_drvdata(pdev);
-
- if (card->hw.rambase) {
- int i;
-
- /* Disable interrupts on the PCI bridge */
- cpc_writew(card->hw.plxbase + card->hw.intctl_reg,
- cpc_readw(card->hw.plxbase + card->hw.intctl_reg) & ~(0x0040));
-
- for (i = 0; i < card->hw.nchan; i++) {
- unregister_hdlc_device(card->chan[i].d.dev);
- }
- iounmap(card->hw.plxbase);
- iounmap(card->hw.scabase);
- iounmap(card->hw.rambase);
- release_mem_region(card->hw.plxphys, card->hw.plxsize);
- release_mem_region(card->hw.ramphys, card->hw.alloc_ramsize);
- release_mem_region(card->hw.scaphys, card->hw.scasize);
- release_region(card->hw.iophys, card->hw.iosize);
- if (card->hw.type == PC300_TE) {
- iounmap(card->hw.falcbase);
- release_mem_region(card->hw.falcphys, card->hw.falcsize);
- }
- for (i = 0; i < card->hw.nchan; i++)
- if (card->chan[i].d.dev)
- free_netdev(card->chan[i].d.dev);
- if (card->hw.irq)
- free_irq(card->hw.irq, card);
- kfree(card);
- pci_disable_device(pdev);
- }
-}
-
-static struct pci_driver cpc_driver = {
- .name = "pc300",
- .id_table = cpc_pci_dev_id,
- .probe = cpc_init_one,
- .remove = __devexit_p(cpc_remove_one),
-};
-
-static int __init cpc_init(void)
-{
- show_version();
- return pci_register_driver(&cpc_driver);
-}
-
-static void __exit cpc_cleanup_module(void)
-{
- pci_unregister_driver(&cpc_driver);
-}
-
-module_init(cpc_init);
-module_exit(cpc_cleanup_module);
-
-MODULE_DESCRIPTION("Cyclades-PC300 cards driver");
-MODULE_AUTHOR( "Author: Ivan Passos <ivan@cyclades.com>\r\n"
- "Maintainer: PC300 Maintainer <pc300@cyclades.com");
-MODULE_LICENSE("GPL");
-
diff --git a/drivers/net/wan/pc300_tty.c b/drivers/net/wan/pc300_tty.c
deleted file mode 100644
index 4709f4228561..000000000000
--- a/drivers/net/wan/pc300_tty.c
+++ /dev/null
@@ -1,1079 +0,0 @@
-/*
- * pc300_tty.c Cyclades-PC300(tm) TTY Driver.
- *
- * Author: Regina Kodato <reginak@cyclades.com>
- *
- * Copyright: (c) 1999-2002 Cyclades Corp.
- *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU General Public License
- * as published by the Free Software Foundation; either version
- * 2 of the License, or (at your option) any later version.
- *
- * $Log: pc300_tty.c,v $
- * Revision 3.7 2002/03/07 14:17:09 henrique
- * License data fixed
- *
- * Revision 3.6 2001/12/10 12:29:42 regina
- * Fix the MLPPP bug
- *
- * Revision 3.5 2001/10/31 11:20:05 regina
- * automatic pppd starts
- *
- * Revision 3.4 2001/08/06 12:01:51 regina
- * problem in DSR_DE bit
- *
- * Revision 3.3 2001/07/26 22:58:41 regina
- * update EDA value
- *
- * Revision 3.2 2001/07/12 13:11:20 regina
- * bug fix - DCD-OFF in pc300 tty driver
- *
- * DMA transmission bug fix
- *
- * Revision 3.1 2001/06/22 13:13:02 regina
- * MLPPP implementation
- *
- */
-
-#include <linux/module.h>
-#include <linux/kernel.h>
-#include <linux/errno.h>
-#include <linux/string.h>
-#include <linux/init.h>
-#include <linux/netdevice.h>
-#include <linux/spinlock.h>
-#include <linux/slab.h>
-#include <linux/if.h>
-#include <linux/skbuff.h>
-/* TTY includes */
-#include <linux/tty.h>
-#include <linux/tty_flip.h>
-#include <linux/serial.h>
-
-#include <asm/io.h>
-#include <asm/uaccess.h>
-
-#include "pc300.h"
-
-/* defines and macros */
-/* TTY Global definitions */
-#define CPC_TTY_NPORTS 8 /* maximum number of the sync tty connections */
-#define CPC_TTY_MAJOR CYCLADES_MAJOR
-#define CPC_TTY_MINOR_START 240 /* minor of the first PC300 interface */
-
-#define CPC_TTY_MAX_MTU 2000
-
-/* tty interface state */
-#define CPC_TTY_ST_IDLE 0
-#define CPC_TTY_ST_INIT 1 /* configured with MLPPP and up */
-#define CPC_TTY_ST_OPEN 2 /* opened by application */
-
-#define CPC_TTY_LOCK(card,flags)\
- do {\
- spin_lock_irqsave(&card->card_lock, flags); \
- } while (0)
-
-#define CPC_TTY_UNLOCK(card,flags) \
- do {\
- spin_unlock_irqrestore(&card->card_lock, flags); \
- } while (0)
-
-//#define CPC_TTY_DBG(format,a...) printk(format,##a)
-#define CPC_TTY_DBG(format,a...)
-
-/* data structures */
-typedef struct _st_cpc_rx_buf {
- struct _st_cpc_rx_buf *next;
- int size;
- unsigned char data[1];
-} st_cpc_rx_buf;
-
-struct st_cpc_rx_list {
- st_cpc_rx_buf *first;
- st_cpc_rx_buf *last;
-};
-
-typedef struct _st_cpc_tty_area {
- int state; /* state of the TTY interface */
- int num_open;
- unsigned int tty_minor; /* minor this interface */
- volatile struct st_cpc_rx_list buf_rx; /* ptr. to reception buffer */
- unsigned char* buf_tx; /* ptr. to transmission buffer */
- pc300dev_t* pc300dev; /* ptr. to info struct in PC300 driver */
- unsigned char name[20]; /* interf. name + "-tty" */
- struct tty_struct *tty;
- struct work_struct tty_tx_work; /* tx work - tx interrupt */
- struct work_struct tty_rx_work; /* rx work - rx interrupt */
- } st_cpc_tty_area;
-
-/* TTY data structures */
-static struct tty_driver serial_drv;
-
-/* local variables */
-static st_cpc_tty_area cpc_tty_area[CPC_TTY_NPORTS];
-
-static int cpc_tty_cnt = 0; /* number of intrfaces configured with MLPPP */
-static int cpc_tty_unreg_flag = 0;
-
-/* TTY functions prototype */
-static int cpc_tty_open(struct tty_struct *tty, struct file *flip);
-static void cpc_tty_close(struct tty_struct *tty, struct file *flip);
-static int cpc_tty_write(struct tty_struct *tty, const unsigned char *buf, int count);
-static int cpc_tty_write_room(struct tty_struct *tty);
-static int cpc_tty_chars_in_buffer(struct tty_struct *tty);
-static void cpc_tty_flush_buffer(struct tty_struct *tty);
-static void cpc_tty_hangup(struct tty_struct *tty);
-static void cpc_tty_rx_work(struct work_struct *work);
-static void cpc_tty_tx_work(struct work_struct *work);
-static int cpc_tty_send_to_card(pc300dev_t *dev,void *buf, int len);
-static void cpc_tty_trace(pc300dev_t *dev, char* buf, int len, char rxtx);
-static void cpc_tty_signal_off(pc300dev_t *pc300dev, unsigned char);
-static void cpc_tty_signal_on(pc300dev_t *pc300dev, unsigned char);
-
-static int pc300_tiocmset(struct tty_struct *, unsigned int, unsigned int);
-static int pc300_tiocmget(struct tty_struct *);
-
-/* functions called by PC300 driver */
-void cpc_tty_init(pc300dev_t *dev);
-void cpc_tty_unregister_service(pc300dev_t *pc300dev);
-void cpc_tty_receive(pc300dev_t *pc300dev);
-void cpc_tty_trigger_poll(pc300dev_t *pc300dev);
-
-/*
- * PC300 TTY clear "signal"
- */
-static void cpc_tty_signal_off(pc300dev_t *pc300dev, unsigned char signal)
-{
- pc300ch_t *pc300chan = (pc300ch_t *)pc300dev->chan;
- pc300_t *card = (pc300_t *) pc300chan->card;
- int ch = pc300chan->channel;
- unsigned long flags;
-
- CPC_TTY_DBG("%s-tty: Clear signal %x\n",
- pc300dev->dev->name, signal);
- CPC_TTY_LOCK(card, flags);
- cpc_writeb(card->hw.scabase + M_REG(CTL,ch),
- cpc_readb(card->hw.scabase+M_REG(CTL,ch))& signal);
- CPC_TTY_UNLOCK(card,flags);
-}
-
-/*
- * PC300 TTY set "signal" to ON
- */
-static void cpc_tty_signal_on(pc300dev_t *pc300dev, unsigned char signal)
-{
- pc300ch_t *pc300chan = (pc300ch_t *)pc300dev->chan;
- pc300_t *card = (pc300_t *) pc300chan->card;
- int ch = pc300chan->channel;
- unsigned long flags;
-
- CPC_TTY_DBG("%s-tty: Set signal %x\n",
- pc300dev->dev->name, signal);
- CPC_TTY_LOCK(card, flags);
- cpc_writeb(card->hw.scabase + M_REG(CTL,ch),
- cpc_readb(card->hw.scabase+M_REG(CTL,ch))& ~signal);
- CPC_TTY_UNLOCK(card,flags);
-}
-
-
-static const struct tty_operations pc300_ops = {
- .open = cpc_tty_open,
- .close = cpc_tty_close,
- .write = cpc_tty_write,
- .write_room = cpc_tty_write_room,
- .chars_in_buffer = cpc_tty_chars_in_buffer,
- .tiocmset = pc300_tiocmset,
- .tiocmget = pc300_tiocmget,
- .flush_buffer = cpc_tty_flush_buffer,
- .hangup = cpc_tty_hangup,
-};
-
-
-/*
- * PC300 TTY initialization routine
- *
- * This routine is called by the PC300 driver during board configuration
- * (ioctl=SIOCSP300CONF). At this point the adapter is completely
- * initialized.
- * o verify kernel version (only 2.4.x)
- * o register TTY driver
- * o init cpc_tty_area struct
- */
-void cpc_tty_init(pc300dev_t *pc300dev)
-{
- unsigned long port;
- int aux;
- st_cpc_tty_area * cpc_tty;
-
- /* hdlcX - X=interface number */
- port = pc300dev->dev->name[4] - '0';
- if (port >= CPC_TTY_NPORTS) {
- printk("%s-tty: invalid interface selected (0-%i): %li",
- pc300dev->dev->name,
- CPC_TTY_NPORTS-1,port);
- return;
- }
-
- if (cpc_tty_cnt == 0) { /* first TTY connection -> register driver */
- CPC_TTY_DBG("%s-tty: driver init, major:%i, minor range:%i=%i\n",
- pc300dev->dev->name,
- CPC_TTY_MAJOR, CPC_TTY_MINOR_START,
- CPC_TTY_MINOR_START+CPC_TTY_NPORTS);
- /* initialize tty driver struct */
- memset(&serial_drv,0,sizeof(struct tty_driver));
- serial_drv.magic = TTY_DRIVER_MAGIC;
- serial_drv.owner = THIS_MODULE;
- serial_drv.driver_name = "pc300_tty";
- serial_drv.name = "ttyCP";
- serial_drv.major = CPC_TTY_MAJOR;
- serial_drv.minor_start = CPC_TTY_MINOR_START;
- serial_drv.num = CPC_TTY_NPORTS;
- serial_drv.type = TTY_DRIVER_TYPE_SERIAL;
- serial_drv.subtype = SERIAL_TYPE_NORMAL;
-
- serial_drv.init_termios = tty_std_termios;
- serial_drv.init_termios.c_cflag = B9600|CS8|CREAD|HUPCL|CLOCAL;
- serial_drv.flags = TTY_DRIVER_REAL_RAW;
-
- /* interface routines from the upper tty layer to the tty driver */
- tty_set_operations(&serial_drv, &pc300_ops);
-
- /* register the TTY driver */
- if (tty_register_driver(&serial_drv)) {
- printk("%s-tty: Failed to register serial driver! ",
- pc300dev->dev->name);
- return;
- }
-
- memset((void *)cpc_tty_area, 0,
- sizeof(st_cpc_tty_area) * CPC_TTY_NPORTS);
- }
-
- cpc_tty = &cpc_tty_area[port];
-
- if (cpc_tty->state != CPC_TTY_ST_IDLE) {
- CPC_TTY_DBG("%s-tty: TTY port %i, already in use.\n",
- pc300dev->dev->name, port);
- return;
- }
-
- cpc_tty_cnt++;
- cpc_tty->state = CPC_TTY_ST_INIT;
- cpc_tty->num_open= 0;
- cpc_tty->tty_minor = port + CPC_TTY_MINOR_START;
- cpc_tty->pc300dev = pc300dev;
-
- INIT_WORK(&cpc_tty->tty_tx_work, cpc_tty_tx_work);
- INIT_WORK(&cpc_tty->tty_rx_work, cpc_tty_rx_work);
-
- cpc_tty->buf_rx.first = cpc_tty->buf_rx.last = NULL;
-
- pc300dev->cpc_tty = (void *)cpc_tty;
-
- aux = strlen(pc300dev->dev->name);
- memcpy(cpc_tty->name, pc300dev->dev->name, aux);
- memcpy(&cpc_tty->name[aux], "-tty", 5);
-
- cpc_open(pc300dev->dev);
- cpc_tty_signal_off(pc300dev, CTL_DTR);
-
- CPC_TTY_DBG("%s: Initializing TTY Sync Driver, tty major#%d minor#%i\n",
- cpc_tty->name,CPC_TTY_MAJOR,cpc_tty->tty_minor);
- return;
-}
-
-/*
- * PC300 TTY OPEN routine
- *
- * This routine is called by the tty driver to open the interface
- * o verify minor
- * o allocate buffer to Rx and Tx
- */
-static int cpc_tty_open(struct tty_struct *tty, struct file *flip)
-{
- int port ;
- st_cpc_tty_area *cpc_tty;
-
- if (!tty) {
- return -ENODEV;
- }
-
- port = tty->index;
-
- if ((port < 0) || (port >= CPC_TTY_NPORTS)){
- CPC_TTY_DBG("pc300_tty: open invalid port %d\n", port);
- return -ENODEV;
- }
-
- cpc_tty = &cpc_tty_area[port];
-
- if (cpc_tty->state == CPC_TTY_ST_IDLE){
- CPC_TTY_DBG("%s: open - invalid interface, port=%d\n",
- cpc_tty->name, tty->index);
- return -ENODEV;
- }
-
- if (cpc_tty->num_open == 0) { /* first open of this tty */
- if (!cpc_tty_area[port].buf_tx){
- cpc_tty_area[port].buf_tx = kmalloc(CPC_TTY_MAX_MTU,GFP_KERNEL);
- if (!cpc_tty_area[port].buf_tx) {
- CPC_TTY_DBG("%s: error in memory allocation\n",cpc_tty->name);
- return -ENOMEM;
- }
- }
-
- if (cpc_tty_area[port].buf_rx.first) {
- unsigned char * aux;
- while (cpc_tty_area[port].buf_rx.first) {
- aux = (unsigned char *)cpc_tty_area[port].buf_rx.first;
- cpc_tty_area[port].buf_rx.first = cpc_tty_area[port].buf_rx.first->next;
- kfree(aux);
- }
- cpc_tty_area[port].buf_rx.first = NULL;
- cpc_tty_area[port].buf_rx.last = NULL;
- }
-
- cpc_tty_area[port].state = CPC_TTY_ST_OPEN;
- cpc_tty_area[port].tty = tty;
- tty->driver_data = &cpc_tty_area[port];
-
- cpc_tty_signal_on(cpc_tty->pc300dev, CTL_DTR);
- }
-
- cpc_tty->num_open++;
-
- CPC_TTY_DBG("%s: opening TTY driver\n", cpc_tty->name);
-
- /* avisar driver PC300 */
- return 0;
-}
-
-/*
- * PC300 TTY CLOSE routine
- *
- * This routine is called by the tty driver to close the interface
- * o call close channel in PC300 driver (cpc_closech)
- * o free Rx and Tx buffers
- */
-
-static void cpc_tty_close(struct tty_struct *tty, struct file *flip)
-{
- st_cpc_tty_area *cpc_tty;
- unsigned long flags;
- int res;
-
- if (!tty || !tty->driver_data ) {
- CPC_TTY_DBG("hdlx-tty: no TTY in close\n");
- return;
- }
-
- cpc_tty = (st_cpc_tty_area *) tty->driver_data;
-
- if ((cpc_tty->tty != tty)|| (cpc_tty->state != CPC_TTY_ST_OPEN)) {
- CPC_TTY_DBG("%s: TTY is not opened\n",cpc_tty->name);
- return;
- }
-
- if (!cpc_tty->num_open) {
- CPC_TTY_DBG("%s: TTY is closed\n",cpc_tty->name);
- return;
- }
-
- if (--cpc_tty->num_open > 0) {
- CPC_TTY_DBG("%s: TTY closed\n",cpc_tty->name);
- return;
- }
-
- cpc_tty_signal_off(cpc_tty->pc300dev, CTL_DTR);
-
- CPC_TTY_LOCK(cpc_tty->pc300dev->chan->card, flags); /* lock irq */
- cpc_tty->tty = NULL;
- cpc_tty->state = CPC_TTY_ST_INIT;
- CPC_TTY_UNLOCK(cpc_tty->pc300dev->chan->card, flags); /* unlock irq */
-
- if (cpc_tty->buf_rx.first) {
- unsigned char * aux;
- while (cpc_tty->buf_rx.first) {
- aux = (unsigned char *)cpc_tty->buf_rx.first;
- cpc_tty->buf_rx.first = cpc_tty->buf_rx.first->next;
- kfree(aux);
- }
- cpc_tty->buf_rx.first = NULL;
- cpc_tty->buf_rx.last = NULL;
- }
-
- kfree(cpc_tty->buf_tx);
- cpc_tty->buf_tx = NULL;
-
- CPC_TTY_DBG("%s: TTY closed\n",cpc_tty->name);
-
- if (!serial_drv.refcount && cpc_tty_unreg_flag) {
- cpc_tty_unreg_flag = 0;
- CPC_TTY_DBG("%s: unregister the tty driver\n", cpc_tty->name);
- if ((res=tty_unregister_driver(&serial_drv))) {
- CPC_TTY_DBG("%s: ERROR ->unregister the tty driver error=%d\n",
- cpc_tty->name,res);
- }
- }
- return;
-}
-
-/*
- * PC300 TTY WRITE routine
- *
- * This routine is called by the tty driver to write a series of characters
- * to the tty device. The characters may come from user or kernel space.
- * o verify the DCD signal
- * o send characters to board and start the transmission
- */
-static int cpc_tty_write(struct tty_struct *tty, const unsigned char *buf, int count)
-{
- st_cpc_tty_area *cpc_tty;
- pc300ch_t *pc300chan;
- pc300_t *card;
- int ch;
- unsigned long flags;
- struct net_device_stats *stats;
-
- if (!tty || !tty->driver_data ) {
- CPC_TTY_DBG("hdlcX-tty: no TTY in write\n");
- return -ENODEV;
- }
-
- cpc_tty = (st_cpc_tty_area *) tty->driver_data;
-
- if ((cpc_tty->tty != tty) || (cpc_tty->state != CPC_TTY_ST_OPEN)) {
- CPC_TTY_DBG("%s: TTY is not opened\n", cpc_tty->name);
- return -ENODEV;
- }
-
- if (count > CPC_TTY_MAX_MTU) {
- CPC_TTY_DBG("%s: count is invalid\n",cpc_tty->name);
- return -EINVAL; /* frame too big */
- }
-
- CPC_TTY_DBG("%s: cpc_tty_write data len=%i\n",cpc_tty->name,count);
-
- pc300chan = (pc300ch_t *)((pc300dev_t*)cpc_tty->pc300dev)->chan;
- stats = &cpc_tty->pc300dev->dev->stats;
- card = (pc300_t *) pc300chan->card;
- ch = pc300chan->channel;
-
- /* verify DCD signal*/
- if (cpc_readb(card->hw.scabase + M_REG(ST3,ch)) & ST3_DCD) {
- /* DCD is OFF */
- CPC_TTY_DBG("%s : DCD is OFF\n", cpc_tty->name);
- stats->tx_errors++;
- stats->tx_carrier_errors++;
- CPC_TTY_LOCK(card, flags);
- cpc_writeb(card->hw.scabase + M_REG(CMD, ch), CMD_TX_BUF_CLR);
-
- if (card->hw.type == PC300_TE) {
- cpc_writeb(card->hw.falcbase + card->hw.cpld_reg2,
- cpc_readb(card->hw.falcbase + card->hw.cpld_reg2) &
- ~(CPLD_REG2_FALC_LED1 << (2 *ch)));
- }
-
- CPC_TTY_UNLOCK(card, flags);
-
- return -EINVAL;
- }
-
- if (cpc_tty_send_to_card(cpc_tty->pc300dev, (void*)buf, count)) {
- /* failed to send */
- CPC_TTY_DBG("%s: trasmition error\n", cpc_tty->name);
- return 0;
- }
- return count;
-}
-
-/*
- * PC300 TTY Write Room routine
- *
- * This routine returns the numbers of characteres the tty driver will accept
- * for queuing to be written.
- * o return MTU
- */
-static int cpc_tty_write_room(struct tty_struct *tty)
-{
- st_cpc_tty_area *cpc_tty;
-
- if (!tty || !tty->driver_data ) {
- CPC_TTY_DBG("hdlcX-tty: no TTY to write room\n");
- return -ENODEV;
- }
-
- cpc_tty = (st_cpc_tty_area *) tty->driver_data;
-
- if ((cpc_tty->tty != tty) || (cpc_tty->state != CPC_TTY_ST_OPEN)) {
- CPC_TTY_DBG("%s: TTY is not opened\n",cpc_tty->name);
- return -ENODEV;
- }
-
- CPC_TTY_DBG("%s: write room\n",cpc_tty->name);
-
- return CPC_TTY_MAX_MTU;
-}
-
-/*
- * PC300 TTY chars in buffer routine
- *
- * This routine returns the chars number in the transmission buffer
- * o returns 0
- */
-static int cpc_tty_chars_in_buffer(struct tty_struct *tty)
-{
- st_cpc_tty_area *cpc_tty;
-
- if (!tty || !tty->driver_data ) {
- CPC_TTY_DBG("hdlcX-tty: no TTY to chars in buffer\n");
- return -ENODEV;
- }
-
- cpc_tty = (st_cpc_tty_area *) tty->driver_data;
-
- if ((cpc_tty->tty != tty) || (cpc_tty->state != CPC_TTY_ST_OPEN)) {
- CPC_TTY_DBG("%s: TTY is not opened\n",cpc_tty->name);
- return -ENODEV;
- }
-
- return 0;
-}
-
-static int pc300_tiocmset(struct tty_struct *tty,
- unsigned int set, unsigned int clear)
-{
- st_cpc_tty_area *cpc_tty;
-
- CPC_TTY_DBG("%s: set:%x clear:%x\n", __func__, set, clear);
-
- if (!tty || !tty->driver_data ) {
- CPC_TTY_DBG("hdlcX-tty: no TTY to chars in buffer\n");
- return -ENODEV;
- }
-
- cpc_tty = (st_cpc_tty_area *) tty->driver_data;
-
- if (set & TIOCM_RTS)
- cpc_tty_signal_on(cpc_tty->pc300dev, CTL_RTS);
- if (set & TIOCM_DTR)
- cpc_tty_signal_on(cpc_tty->pc300dev, CTL_DTR);
-
- if (clear & TIOCM_RTS)
- cpc_tty_signal_off(cpc_tty->pc300dev, CTL_RTS);
- if (clear & TIOCM_DTR)
- cpc_tty_signal_off(cpc_tty->pc300dev, CTL_DTR);
-
- return 0;
-}
-
-static int pc300_tiocmget(struct tty_struct *tty)
-{
- unsigned int result;
- unsigned char status;
- unsigned long flags;
- st_cpc_tty_area *cpc_tty = (st_cpc_tty_area *) tty->driver_data;
- pc300dev_t *pc300dev = cpc_tty->pc300dev;
- pc300ch_t *pc300chan = (pc300ch_t *)pc300dev->chan;
- pc300_t *card = (pc300_t *) pc300chan->card;
- int ch = pc300chan->channel;
-
- cpc_tty = (st_cpc_tty_area *) tty->driver_data;
-
- CPC_TTY_DBG("%s-tty: tiocmget\n",
- ((struct net_device*)(pc300dev->hdlc))->name);
-
- CPC_TTY_LOCK(card, flags);
- status = cpc_readb(card->hw.scabase+M_REG(CTL,ch));
- CPC_TTY_UNLOCK(card,flags);
-
- result = ((status & CTL_DTR) ? TIOCM_DTR : 0) |
- ((status & CTL_RTS) ? TIOCM_RTS : 0);
-
- return result;
-}
-
-/*
- * PC300 TTY Flush Buffer routine
- *
- * This routine resets the transmission buffer
- */
-static void cpc_tty_flush_buffer(struct tty_struct *tty)
-{
- st_cpc_tty_area *cpc_tty;
-
- if (!tty || !tty->driver_data ) {
- CPC_TTY_DBG("hdlcX-tty: no TTY to flush buffer\n");
- return;
- }
-
- cpc_tty = (st_cpc_tty_area *) tty->driver_data;
-
- if ((cpc_tty->tty != tty) || (cpc_tty->state != CPC_TTY_ST_OPEN)) {
- CPC_TTY_DBG("%s: TTY is not opened\n",cpc_tty->name);
- return;
- }
-
- CPC_TTY_DBG("%s: call wake_up_interruptible\n",cpc_tty->name);
-
- tty_wakeup(tty);
- return;
-}
-
-/*
- * PC300 TTY Hangup routine
- *
- * This routine is called by the tty driver to hangup the interface
- * o clear DTR signal
- */
-
-static void cpc_tty_hangup(struct tty_struct *tty)
-{
- st_cpc_tty_area *cpc_tty;
- int res;
-
- if (!tty || !tty->driver_data ) {
- CPC_TTY_DBG("hdlcX-tty: no TTY to hangup\n");
- return ;
- }
-
- cpc_tty = (st_cpc_tty_area *) tty->driver_data;
-
- if ((cpc_tty->tty != tty) || (cpc_tty->state != CPC_TTY_ST_OPEN)) {
- CPC_TTY_DBG("%s: TTY is not opened\n",cpc_tty->name);
- return ;
- }
- if (!serial_drv.refcount && cpc_tty_unreg_flag) {
- cpc_tty_unreg_flag = 0;
- CPC_TTY_DBG("%s: unregister the tty driver\n", cpc_tty->name);
- if ((res=tty_unregister_driver(&serial_drv))) {
- CPC_TTY_DBG("%s: ERROR ->unregister the tty driver error=%d\n",
- cpc_tty->name,res);
- }
- }
- cpc_tty_signal_off(cpc_tty->pc300dev, CTL_DTR);
-}
-
-/*
- * PC300 TTY RX work routine
- * This routine treats RX work
- * o verify read buffer
- * o call the line disc. read
- * o free memory
- */
-static void cpc_tty_rx_work(struct work_struct *work)
-{
- st_cpc_tty_area *cpc_tty;
- unsigned long port;
- int i, j;
- volatile st_cpc_rx_buf *buf;
- char flags=0,flg_rx=1;
- struct tty_ldisc *ld;
-
- if (cpc_tty_cnt == 0) return;
-
- for (i=0; (i < 4) && flg_rx ; i++) {
- flg_rx = 0;
-
- cpc_tty = container_of(work, st_cpc_tty_area, tty_rx_work);
- port = cpc_tty - cpc_tty_area;
-
- for (j=0; j < CPC_TTY_NPORTS; j++) {
- cpc_tty = &cpc_tty_area[port];
-
- if ((buf=cpc_tty->buf_rx.first) != NULL) {
- if (cpc_tty->tty) {
- ld = tty_ldisc_ref(cpc_tty->tty);
- if (ld) {
- if (ld->ops->receive_buf) {
- CPC_TTY_DBG("%s: call line disc. receive_buf\n",cpc_tty->name);
- ld->ops->receive_buf(cpc_tty->tty, (char *)(buf->data), &flags, buf->size);
- }
- tty_ldisc_deref(ld);
- }
- }
- cpc_tty->buf_rx.first = cpc_tty->buf_rx.first->next;
- kfree((void *)buf);
- buf = cpc_tty->buf_rx.first;
- flg_rx = 1;
- }
- if (++port == CPC_TTY_NPORTS) port = 0;
- }
- }
-}
-
-/*
- * PC300 TTY RX work routine
- *
- * This routine treats RX interrupt.
- * o read all frames in card
- * o verify the frame size
- * o read the frame in rx buffer
- */
-static void cpc_tty_rx_disc_frame(pc300ch_t *pc300chan)
-{
- volatile pcsca_bd_t __iomem * ptdescr;
- volatile unsigned char status;
- pc300_t *card = (pc300_t *)pc300chan->card;
- int ch = pc300chan->channel;
-
- /* dma buf read */
- ptdescr = (pcsca_bd_t __iomem *)(card->hw.rambase +
- RX_BD_ADDR(ch, pc300chan->rx_first_bd));
- while (pc300chan->rx_first_bd != pc300chan->rx_last_bd) {
- status = cpc_readb(&ptdescr->status);
- cpc_writeb(&ptdescr->status, 0);
- cpc_writeb(&ptdescr->len, 0);
- pc300chan->rx_first_bd = (pc300chan->rx_first_bd + 1) &
- (N_DMA_RX_BUF - 1);
- if (status & DST_EOM) {
- break; /* end of message */
- }
- ptdescr = (pcsca_bd_t __iomem *)(card->hw.rambase + cpc_readl(&ptdescr->next));
- }
-}
-
-void cpc_tty_receive(pc300dev_t *pc300dev)
-{
- st_cpc_tty_area *cpc_tty;
- pc300ch_t *pc300chan = (pc300ch_t *)pc300dev->chan;
- pc300_t *card = (pc300_t *)pc300chan->card;
- int ch = pc300chan->channel;
- volatile pcsca_bd_t __iomem * ptdescr;
- struct net_device_stats *stats = &pc300dev->dev->stats;
- int rx_len, rx_aux;
- volatile unsigned char status;
- unsigned short first_bd = pc300chan->rx_first_bd;
- st_cpc_rx_buf *new = NULL;
- unsigned char dsr_rx;
-
- if (pc300dev->cpc_tty == NULL) {
- return;
- }
-
- dsr_rx = cpc_readb(card->hw.scabase + DSR_RX(ch));
-
- cpc_tty = pc300dev->cpc_tty;
-
- while (1) {
- rx_len = 0;
- ptdescr = (pcsca_bd_t __iomem *)(card->hw.rambase + RX_BD_ADDR(ch, first_bd));
- while ((status = cpc_readb(&ptdescr->status)) & DST_OSB) {
- rx_len += cpc_readw(&ptdescr->len);
- first_bd = (first_bd + 1) & (N_DMA_RX_BUF - 1);
- if (status & DST_EOM) {
- break;
- }
- ptdescr = (pcsca_bd_t __iomem *)(card->hw.rambase+cpc_readl(&ptdescr->next));
- }
-
- if (!rx_len) {
- if (dsr_rx & DSR_BOF) {
- /* update EDA */
- cpc_writel(card->hw.scabase + DRX_REG(EDAL, ch),
- RX_BD_ADDR(ch, pc300chan->rx_last_bd));
- }
- kfree(new);
- return;
- }
-
- if (rx_len > CPC_TTY_MAX_MTU) {
- /* Free RX descriptors */
- CPC_TTY_DBG("%s: frame size is invalid.\n",cpc_tty->name);
- stats->rx_errors++;
- stats->rx_frame_errors++;
- cpc_tty_rx_disc_frame(pc300chan);
- continue;
- }
-
- new = kmalloc(rx_len + sizeof(st_cpc_rx_buf), GFP_ATOMIC);
- if (!new) {
- cpc_tty_rx_disc_frame(pc300chan);
- continue;
- }
-
- /* dma buf read */
- ptdescr = (pcsca_bd_t __iomem *)(card->hw.rambase +
- RX_BD_ADDR(ch, pc300chan->rx_first_bd));
-
- rx_len = 0; /* counter frame size */
-
- while ((status = cpc_readb(&ptdescr->status)) & DST_OSB) {
- rx_aux = cpc_readw(&ptdescr->len);
- if ((status & (DST_OVR | DST_CRC | DST_RBIT | DST_SHRT | DST_ABT))
- || (rx_aux > BD_DEF_LEN)) {
- CPC_TTY_DBG("%s: reception error\n", cpc_tty->name);
- stats->rx_errors++;
- if (status & DST_OVR) {
- stats->rx_fifo_errors++;
- }
- if (status & DST_CRC) {
- stats->rx_crc_errors++;
- }
- if ((status & (DST_RBIT | DST_SHRT | DST_ABT)) ||
- (rx_aux > BD_DEF_LEN)) {
- stats->rx_frame_errors++;
- }
- /* discard remainig descriptors used by the bad frame */
- CPC_TTY_DBG("%s: reception error - discard descriptors",
- cpc_tty->name);
- cpc_tty_rx_disc_frame(pc300chan);
- rx_len = 0;
- kfree(new);
- new = NULL;
- break; /* read next frame - while(1) */
- }
-
- if (cpc_tty->state != CPC_TTY_ST_OPEN) {
- /* Free RX descriptors */
- cpc_tty_rx_disc_frame(pc300chan);
- stats->rx_dropped++;
- rx_len = 0;
- kfree(new);
- new = NULL;
- break; /* read next frame - while(1) */
- }
-
- /* read the segment of the frame */
- if (rx_aux != 0) {
- memcpy_fromio((new->data + rx_len),
- (void __iomem *)(card->hw.rambase +
- cpc_readl(&ptdescr->ptbuf)), rx_aux);
- rx_len += rx_aux;
- }
- cpc_writeb(&ptdescr->status,0);
- cpc_writeb(&ptdescr->len, 0);
- pc300chan->rx_first_bd = (pc300chan->rx_first_bd + 1) &
- (N_DMA_RX_BUF -1);
- if (status & DST_EOM)break;
-
- ptdescr = (pcsca_bd_t __iomem *) (card->hw.rambase +
- cpc_readl(&ptdescr->next));
- }
- /* update pointer */
- pc300chan->rx_last_bd = (pc300chan->rx_first_bd - 1) &
- (N_DMA_RX_BUF - 1) ;
- if (!(dsr_rx & DSR_BOF)) {
- /* update EDA */
- cpc_writel(card->hw.scabase + DRX_REG(EDAL, ch),
- RX_BD_ADDR(ch, pc300chan->rx_last_bd));
- }
- if (rx_len != 0) {
- stats->rx_bytes += rx_len;
-
- if (pc300dev->trace_on) {
- cpc_tty_trace(pc300dev, new->data,rx_len, 'R');
- }
- new->size = rx_len;
- new->next = NULL;
- if (cpc_tty->buf_rx.first == NULL) {
- cpc_tty->buf_rx.first = new;
- cpc_tty->buf_rx.last = new;
- } else {
- cpc_tty->buf_rx.last->next = new;
- cpc_tty->buf_rx.last = new;
- }
- schedule_work(&(cpc_tty->tty_rx_work));
- stats->rx_packets++;
- }
- }
-}
-
-/*
- * PC300 TTY TX work routine
- *
- * This routine treats TX interrupt.
- * o if need call line discipline wakeup
- * o call wake_up_interruptible
- */
-static void cpc_tty_tx_work(struct work_struct *work)
-{
- st_cpc_tty_area *cpc_tty =
- container_of(work, st_cpc_tty_area, tty_tx_work);
- struct tty_struct *tty;
-
- CPC_TTY_DBG("%s: cpc_tty_tx_work init\n",cpc_tty->name);
-
- if ((tty = cpc_tty->tty) == NULL) {
- CPC_TTY_DBG("%s: the interface is not opened\n",cpc_tty->name);
- return;
- }
- tty_wakeup(tty);
-}
-
-/*
- * PC300 TTY send to card routine
- *
- * This routine send data to card.
- * o clear descriptors
- * o write data to DMA buffers
- * o start the transmission
- */
-static int cpc_tty_send_to_card(pc300dev_t *dev,void* buf, int len)
-{
- pc300ch_t *chan = (pc300ch_t *)dev->chan;
- pc300_t *card = (pc300_t *)chan->card;
- int ch = chan->channel;
- struct net_device_stats *stats = &dev->dev->stats;
- unsigned long flags;
- volatile pcsca_bd_t __iomem *ptdescr;
- int i, nchar;
- int tosend = len;
- int nbuf = ((len - 1)/BD_DEF_LEN) + 1;
- unsigned char *pdata=buf;
-
- CPC_TTY_DBG("%s:cpc_tty_send_to_cars len=%i",
- (st_cpc_tty_area *)dev->cpc_tty->name,len);
-
- if (nbuf >= card->chan[ch].nfree_tx_bd) {
- return 1;
- }
-
- /* write buffer to DMA buffers */
- CPC_TTY_DBG("%s: call dma_buf_write\n",
- (st_cpc_tty_area *)dev->cpc_tty->name);
- for (i = 0 ; i < nbuf ; i++) {
- ptdescr = (pcsca_bd_t __iomem *)(card->hw.rambase +
- TX_BD_ADDR(ch, card->chan[ch].tx_next_bd));
- nchar = (BD_DEF_LEN > tosend) ? tosend : BD_DEF_LEN;
- if (cpc_readb(&ptdescr->status) & DST_OSB) {
- memcpy_toio((void __iomem *)(card->hw.rambase +
- cpc_readl(&ptdescr->ptbuf)),
- &pdata[len - tosend],
- nchar);
- card->chan[ch].nfree_tx_bd--;
- if ((i + 1) == nbuf) {
- /* This must be the last BD to be used */
- cpc_writeb(&ptdescr->status, DST_EOM);
- } else {
- cpc_writeb(&ptdescr->status, 0);
- }
- cpc_writew(&ptdescr->len, nchar);
- } else {
- CPC_TTY_DBG("%s: error in dma_buf_write\n",
- (st_cpc_tty_area *)dev->cpc_tty->name);
- stats->tx_dropped++;
- return 1;
- }
- tosend -= nchar;
- card->chan[ch].tx_next_bd =
- (card->chan[ch].tx_next_bd + 1) & (N_DMA_TX_BUF - 1);
- }
-
- if (dev->trace_on) {
- cpc_tty_trace(dev, buf, len,'T');
- }
-
- /* start transmission */
- CPC_TTY_DBG("%s: start transmission\n",
- (st_cpc_tty_area *)dev->cpc_tty->name);
-
- CPC_TTY_LOCK(card, flags);
- cpc_writeb(card->hw.scabase + DTX_REG(EDAL, ch),
- TX_BD_ADDR(ch, chan->tx_next_bd));
- cpc_writeb(card->hw.scabase + M_REG(CMD, ch), CMD_TX_ENA);
- cpc_writeb(card->hw.scabase + DSR_TX(ch), DSR_DE);
-
- if (card->hw.type == PC300_TE) {
- cpc_writeb(card->hw.falcbase + card->hw.cpld_reg2,
- cpc_readb(card->hw.falcbase + card->hw.cpld_reg2) |
- (CPLD_REG2_FALC_LED1 << (2 * ch)));
- }
- CPC_TTY_UNLOCK(card, flags);
- return 0;
-}
-
-/*
- * PC300 TTY trace routine
- *
- * This routine send trace of connection to application.
- * o clear descriptors
- * o write data to DMA buffers
- * o start the transmission
- */
-
-static void cpc_tty_trace(pc300dev_t *dev, char* buf, int len, char rxtx)
-{
- struct sk_buff *skb;
-
- if ((skb = dev_alloc_skb(10 + len)) == NULL) {
- /* out of memory */
- CPC_TTY_DBG("%s: tty_trace - out of memory\n", dev->dev->name);
- return;
- }
-
- skb_put (skb, 10 + len);
- skb->dev = dev->dev;
- skb->protocol = htons(ETH_P_CUST);
- skb_reset_mac_header(skb);
- skb->pkt_type = PACKET_HOST;
- skb->len = 10 + len;
-
- skb_copy_to_linear_data(skb, dev->dev->name, 5);
- skb->data[5] = '[';
- skb->data[6] = rxtx;
- skb->data[7] = ']';
- skb->data[8] = ':';
- skb->data[9] = ' ';
- skb_copy_to_linear_data_offset(skb, 10, buf, len);
- netif_rx(skb);
-}
-
-/*
- * PC300 TTY unregister service routine
- *
- * This routine unregister one interface.
- */
-void cpc_tty_unregister_service(pc300dev_t *pc300dev)
-{
- st_cpc_tty_area *cpc_tty;
- ulong flags;
- int res;
-
- if ((cpc_tty= (st_cpc_tty_area *) pc300dev->cpc_tty) == NULL) {
- CPC_TTY_DBG("%s: interface is not TTY\n", pc300dev->dev->name);
- return;
- }
- CPC_TTY_DBG("%s: cpc_tty_unregister_service", cpc_tty->name);
-
- if (cpc_tty->pc300dev != pc300dev) {
- CPC_TTY_DBG("%s: invalid tty ptr=%s\n",
- pc300dev->dev->name, cpc_tty->name);
- return;
- }
-
- if (--cpc_tty_cnt == 0) {
- if (serial_drv.refcount) {
- CPC_TTY_DBG("%s: unregister is not possible, refcount=%d",
- cpc_tty->name, serial_drv.refcount);
- cpc_tty_cnt++;
- cpc_tty_unreg_flag = 1;
- return;
- } else {
- CPC_TTY_DBG("%s: unregister the tty driver\n", cpc_tty->name);
- if ((res=tty_unregister_driver(&serial_drv))) {
- CPC_TTY_DBG("%s: ERROR ->unregister the tty driver error=%d\n",
- cpc_tty->name,res);
- }
- }
- }
- CPC_TTY_LOCK(pc300dev->chan->card,flags);
- cpc_tty->tty = NULL;
- CPC_TTY_UNLOCK(pc300dev->chan->card, flags);
- cpc_tty->tty_minor = 0;
- cpc_tty->state = CPC_TTY_ST_IDLE;
-}
-
-/*
- * PC300 TTY trigger poll routine
- * This routine is called by pc300driver to treats Tx interrupt.
- */
-void cpc_tty_trigger_poll(pc300dev_t *pc300dev)
-{
- st_cpc_tty_area *cpc_tty = (st_cpc_tty_area *)pc300dev->cpc_tty;
- if (!cpc_tty) {
- return;
- }
- schedule_work(&(cpc_tty->tty_tx_work));
-}
diff --git a/drivers/net/wireless/at76c50x-usb.c b/drivers/net/wireless/at76c50x-usb.c
index 3df0146b797e..efc162e0b511 100644
--- a/drivers/net/wireless/at76c50x-usb.c
+++ b/drivers/net/wireless/at76c50x-usb.c
@@ -1955,7 +1955,7 @@ static int at76_hw_scan(struct ieee80211_hw *hw,
ret = at76_set_card_command(priv->udev, CMD_SCAN, &scan, sizeof(scan));
if (ret < 0) {
- err("CMD_SCAN failed: %d", ret);
+ wiphy_err(priv->hw->wiphy, "CMD_SCAN failed: %d\n", ret);
goto exit;
}
@@ -2486,6 +2486,7 @@ static struct usb_driver at76_driver = {
.probe = at76_probe,
.disconnect = at76_disconnect,
.id_table = dev_table,
+ .disable_hub_initiated_lpm = 1,
};
static int __init at76_mod_init(void)
diff --git a/drivers/net/wireless/ath/ath6kl/usb.c b/drivers/net/wireless/ath/ath6kl/usb.c
index ec7f1f5fd1ca..44a795f14da9 100644
--- a/drivers/net/wireless/ath/ath6kl/usb.c
+++ b/drivers/net/wireless/ath/ath6kl/usb.c
@@ -1182,6 +1182,7 @@ static struct usb_driver ath6kl_usb_driver = {
.disconnect = ath6kl_usb_remove,
.id_table = ath6kl_usb_ids,
.supports_autosuspend = true,
+ .disable_hub_initiated_lpm = 1,
};
static int ath6kl_usb_init(void)
diff --git a/drivers/net/wireless/ath/ath9k/hif_usb.c b/drivers/net/wireless/ath/ath9k/hif_usb.c
index f67cd952e741..aa327adcc3d8 100644
--- a/drivers/net/wireless/ath/ath9k/hif_usb.c
+++ b/drivers/net/wireless/ath/ath9k/hif_usb.c
@@ -1358,6 +1358,7 @@ static struct usb_driver ath9k_hif_usb_driver = {
#endif
.id_table = ath9k_hif_usb_ids,
.soft_unbind = 1,
+ .disable_hub_initiated_lpm = 1,
};
int ath9k_hif_usb_init(void)
diff --git a/drivers/net/wireless/ath/carl9170/usb.c b/drivers/net/wireless/ath/carl9170/usb.c
index 89821e4835c7..888152ce3eca 100644
--- a/drivers/net/wireless/ath/carl9170/usb.c
+++ b/drivers/net/wireless/ath/carl9170/usb.c
@@ -1159,6 +1159,7 @@ static struct usb_driver carl9170_driver = {
.resume = carl9170_usb_resume,
.reset_resume = carl9170_usb_resume,
#endif /* CONFIG_PM */
+ .disable_hub_initiated_lpm = 1,
};
module_usb_driver(carl9170_driver);
diff --git a/drivers/net/wireless/brcm80211/brcmfmac/usb.c b/drivers/net/wireless/brcm80211/brcmfmac/usb.c
index 1d67ecf681b7..c5a34ffe6459 100644
--- a/drivers/net/wireless/brcm80211/brcmfmac/usb.c
+++ b/drivers/net/wireless/brcm80211/brcmfmac/usb.c
@@ -1596,7 +1596,8 @@ static struct usb_driver brcmf_usbdrvr = {
.id_table = brcmf_usb_devid_table,
.suspend = brcmf_usb_suspend,
.resume = brcmf_usb_resume,
- .supports_autosuspend = 1
+ .supports_autosuspend = 1,
+ .disable_hub_initiated_lpm = 1,
};
void brcmf_usb_exit(void)
diff --git a/drivers/net/wireless/libertas/if_usb.c b/drivers/net/wireless/libertas/if_usb.c
index 75403e6e3990..cd3b0d400618 100644
--- a/drivers/net/wireless/libertas/if_usb.c
+++ b/drivers/net/wireless/libertas/if_usb.c
@@ -1011,6 +1011,7 @@ static struct usb_driver if_usb_driver = {
.suspend = if_usb_suspend,
.resume = if_usb_resume,
.reset_resume = if_usb_resume,
+ .disable_hub_initiated_lpm = 1,
};
module_usb_driver(if_usb_driver);
diff --git a/drivers/net/wireless/libertas_tf/if_usb.c b/drivers/net/wireless/libertas_tf/if_usb.c
index 7ced130f4f9e..19a5a92dd779 100644
--- a/drivers/net/wireless/libertas_tf/if_usb.c
+++ b/drivers/net/wireless/libertas_tf/if_usb.c
@@ -920,6 +920,7 @@ static struct usb_driver if_usb_driver = {
.id_table = if_usb_table,
.suspend = if_usb_suspend,
.resume = if_usb_resume,
+ .disable_hub_initiated_lpm = 1,
};
module_usb_driver(if_usb_driver);
diff --git a/drivers/net/wireless/orinoco/orinoco_usb.c b/drivers/net/wireless/orinoco/orinoco_usb.c
index f634d4582bfe..7f53cea2f205 100644
--- a/drivers/net/wireless/orinoco/orinoco_usb.c
+++ b/drivers/net/wireless/orinoco/orinoco_usb.c
@@ -1752,6 +1752,7 @@ static struct usb_driver orinoco_driver = {
.probe = ezusb_probe,
.disconnect = ezusb_disconnect,
.id_table = ezusb_table,
+ .disable_hub_initiated_lpm = 1,
};
module_usb_driver(orinoco_driver);
diff --git a/drivers/net/wireless/p54/p54usb.c b/drivers/net/wireless/p54/p54usb.c
index e1eac830e2fc..7f207b6e9552 100644
--- a/drivers/net/wireless/p54/p54usb.c
+++ b/drivers/net/wireless/p54/p54usb.c
@@ -1140,6 +1140,7 @@ static struct usb_driver p54u_driver = {
.reset_resume = p54u_resume,
#endif /* CONFIG_PM */
.soft_unbind = 1,
+ .disable_hub_initiated_lpm = 1,
};
module_usb_driver(p54u_driver);
diff --git a/drivers/net/wireless/rndis_wlan.c b/drivers/net/wireless/rndis_wlan.c
index b91d1bb30b41..c5404eb82b2f 100644
--- a/drivers/net/wireless/rndis_wlan.c
+++ b/drivers/net/wireless/rndis_wlan.c
@@ -3765,6 +3765,7 @@ static struct usb_driver rndis_wlan_driver = {
.disconnect = usbnet_disconnect,
.suspend = usbnet_suspend,
.resume = usbnet_resume,
+ .disable_hub_initiated_lpm = 1,
};
module_usb_driver(rndis_wlan_driver);
diff --git a/drivers/net/wireless/rt2x00/rt2500usb.c b/drivers/net/wireless/rt2x00/rt2500usb.c
index c88fd3e61090..669aecdb411d 100644
--- a/drivers/net/wireless/rt2x00/rt2500usb.c
+++ b/drivers/net/wireless/rt2x00/rt2500usb.c
@@ -1980,6 +1980,7 @@ static struct usb_driver rt2500usb_driver = {
.disconnect = rt2x00usb_disconnect,
.suspend = rt2x00usb_suspend,
.resume = rt2x00usb_resume,
+ .disable_hub_initiated_lpm = 1,
};
module_usb_driver(rt2500usb_driver);
diff --git a/drivers/net/wireless/rt2x00/rt2800usb.c b/drivers/net/wireless/rt2x00/rt2800usb.c
index 5601302d09ad..bf78317a6adb 100644
--- a/drivers/net/wireless/rt2x00/rt2800usb.c
+++ b/drivers/net/wireless/rt2x00/rt2800usb.c
@@ -1302,6 +1302,7 @@ static struct usb_driver rt2800usb_driver = {
.disconnect = rt2x00usb_disconnect,
.suspend = rt2x00usb_suspend,
.resume = rt2x00usb_resume,
+ .disable_hub_initiated_lpm = 1,
};
module_usb_driver(rt2800usb_driver);
diff --git a/drivers/net/wireless/rt2x00/rt73usb.c b/drivers/net/wireless/rt2x00/rt73usb.c
index 155136691a38..77ccbbc7da41 100644
--- a/drivers/net/wireless/rt2x00/rt73usb.c
+++ b/drivers/net/wireless/rt2x00/rt73usb.c
@@ -2527,6 +2527,7 @@ static struct usb_driver rt73usb_driver = {
.disconnect = rt2x00usb_disconnect,
.suspend = rt2x00usb_suspend,
.resume = rt2x00usb_resume,
+ .disable_hub_initiated_lpm = 1,
};
module_usb_driver(rt73usb_driver);
diff --git a/drivers/net/wireless/rtl818x/rtl8187/dev.c b/drivers/net/wireless/rtl818x/rtl8187/dev.c
index d8114962b0c9..4fb1ca1b86b9 100644
--- a/drivers/net/wireless/rtl818x/rtl8187/dev.c
+++ b/drivers/net/wireless/rtl818x/rtl8187/dev.c
@@ -1663,6 +1663,7 @@ static struct usb_driver rtl8187_driver = {
.id_table = rtl8187_table,
.probe = rtl8187_probe,
.disconnect = __devexit_p(rtl8187_disconnect),
+ .disable_hub_initiated_lpm = 1,
};
module_usb_driver(rtl8187_driver);
diff --git a/drivers/net/wireless/rtlwifi/rtl8192cu/sw.c b/drivers/net/wireless/rtlwifi/rtl8192cu/sw.c
index 7737fb0c6661..d228358e6a40 100644
--- a/drivers/net/wireless/rtlwifi/rtl8192cu/sw.c
+++ b/drivers/net/wireless/rtlwifi/rtl8192cu/sw.c
@@ -373,6 +373,7 @@ static struct usb_driver rtl8192cu_driver = {
#ifdef CONFIG_AUTOSUSPEND
.supports_autosuspend = 1,
#endif
+ .disable_hub_initiated_lpm = 1,
};
module_usb_driver(rtl8192cu_driver);
diff --git a/drivers/net/wireless/zd1201.c b/drivers/net/wireless/zd1201.c
index a66b93b7ff9a..48273dd05b63 100644
--- a/drivers/net/wireless/zd1201.c
+++ b/drivers/net/wireless/zd1201.c
@@ -1905,6 +1905,7 @@ static struct usb_driver zd1201_usb = {
.id_table = zd1201_table,
.suspend = zd1201_suspend,
.resume = zd1201_resume,
+ .disable_hub_initiated_lpm = 1,
};
module_usb_driver(zd1201_usb);
diff --git a/drivers/net/wireless/zd1211rw/zd_usb.c b/drivers/net/wireless/zd1211rw/zd_usb.c
index f766b3e67c6d..af83c43bcdb1 100644
--- a/drivers/net/wireless/zd1211rw/zd_usb.c
+++ b/drivers/net/wireless/zd1211rw/zd_usb.c
@@ -1542,6 +1542,7 @@ static struct usb_driver driver = {
.disconnect = disconnect,
.pre_reset = pre_reset,
.post_reset = post_reset,
+ .disable_hub_initiated_lpm = 1,
};
struct workqueue_struct *zd_workqueue;