Commit 0500df7b authored by Kai Germaschewski's avatar Kai Germaschewski

ISDN: Add support for USR PCI TA

(by Karsten Keil)
parent f3fc213e
...@@ -52,6 +52,7 @@ Sedlbauer Speed Card (Speed Win, Teledat 100, PCI, Fax+) ...@@ -52,6 +52,7 @@ Sedlbauer Speed Card (Speed Win, Teledat 100, PCI, Fax+)
Sedlbauer Speed Star/Speed Star2 (PCMCIA) Sedlbauer Speed Star/Speed Star2 (PCMCIA)
Sedlbauer ISDN-Controller PC/104 Sedlbauer ISDN-Controller PC/104
USR Sportster internal TA (compatible Stollmann tina-pp V3) USR Sportster internal TA (compatible Stollmann tina-pp V3)
USR internal TA PCI
ith Kommunikationstechnik GmbH MIC 16 ISA card ith Kommunikationstechnik GmbH MIC 16 ISA card
Traverse Technologie NETjet PCI S0 card and NETspider U card Traverse Technologie NETjet PCI S0 card and NETspider U card
Ovislink ISDN sc100-p card (NETjet driver) Ovislink ISDN sc100-p card (NETjet driver)
......
...@@ -29,11 +29,17 @@ typedef struct { ...@@ -29,11 +29,17 @@ typedef struct {
static const PCI_ENTRY id_list[] = static const PCI_ENTRY id_list[] =
{ {
{PCI_VENDOR_ID_DYNALINK, PCI_DEVICE_ID_DYNALINK_IS64PH, "Dynalink/AsusCom", "IS64PH"},
{PCI_VENDOR_ID_WINBOND2, PCI_DEVICE_ID_WINBOND2_6692, "Winbond", "W6692"}, {PCI_VENDOR_ID_WINBOND2, PCI_DEVICE_ID_WINBOND2_6692, "Winbond", "W6692"},
{0, 0, NULL, NULL} {PCI_VENDOR_ID_DYNALINK, PCI_DEVICE_ID_DYNALINK_IS64PH, "Dynalink/AsusCom", "IS64PH"},
{0, 0, "U.S.Robotics", "ISDN PCI Card TA"}
}; };
#define W6692_SV_USR 0x16ec
#define W6692_SD_USR 0x3409
#define W6692_WINBOND 0
#define W6692_DYNALINK 1
#define W6692_USR 2
extern const char *CardType[]; extern const char *CardType[];
const char *w6692_revision = "$Revision: 1.12.6.6 $"; const char *w6692_revision = "$Revision: 1.12.6.6 $";
...@@ -859,6 +865,28 @@ setstack_w6692(struct PStack *st, struct BCState *bcs) ...@@ -859,6 +865,28 @@ setstack_w6692(struct PStack *st, struct BCState *bcs)
return (0); return (0);
} }
void resetW6692(struct IsdnCardState *cs)
{
cs->writeW6692(cs, W_D_CTL, W_D_CTL_SRST);
schedule_timeout((10*HZ)/1000);
cs->writeW6692(cs, W_D_CTL, 0x00);
schedule_timeout((10*HZ)/1000);
cs->writeW6692(cs, W_IMASK, 0xff);
cs->writeW6692(cs, W_D_SAM, 0xff);
cs->writeW6692(cs, W_D_TAM, 0xff);
cs->writeW6692(cs, W_D_EXIM, 0x00);
cs->writeW6692(cs, W_D_MODE, W_D_MODE_RACT);
cs->writeW6692(cs, W_IMASK, 0x18);
if (cs->subtyp == W6692_USR) {
/* seems that USR implemented some power control features
* Pin 79 is connected to the oscilator circuit so we
* have to handle it here
*/
cs->writeW6692(cs, W_PCTL, 0x80);
cs->writeW6692(cs, W_XDATA, 0x00);
}
}
void __init initW6692(struct IsdnCardState *cs, int part) void __init initW6692(struct IsdnCardState *cs, int part)
{ {
if (part & 1) { if (part & 1) {
...@@ -868,15 +896,7 @@ void __init initW6692(struct IsdnCardState *cs, int part) ...@@ -868,15 +896,7 @@ void __init initW6692(struct IsdnCardState *cs, int part)
cs->dbusytimer.function = (void *) dbusy_timer_handler; cs->dbusytimer.function = (void *) dbusy_timer_handler;
cs->dbusytimer.data = (long) cs; cs->dbusytimer.data = (long) cs;
init_timer(&cs->dbusytimer); init_timer(&cs->dbusytimer);
resetW6692(cs);
cs->writeW6692(cs, W_D_CTL, W_D_CTL_SRST);
cs->writeW6692(cs, W_D_CTL, 0x00);
cs->writeW6692(cs, W_IMASK, 0xff);
cs->writeW6692(cs, W_D_SAM, 0xff);
cs->writeW6692(cs, W_D_TAM, 0xff);
cs->writeW6692(cs, W_D_EXIM, 0x00);
cs->writeW6692(cs, W_D_MODE, W_D_MODE_RACT);
cs->writeW6692(cs, W_IMASK, 0x18);
ph_command(cs, W_L1CMD_RST); ph_command(cs, W_L1CMD_RST);
cs->dc.w6692.ph_state = W_L1CMD_RST; cs->dc.w6692.ph_state = W_L1CMD_RST;
W6692_new_ph(cs); W6692_new_ph(cs);
...@@ -943,9 +963,14 @@ w6692_card_msg(struct IsdnCardState *cs, int mt, void *arg) ...@@ -943,9 +963,14 @@ w6692_card_msg(struct IsdnCardState *cs, int mt, void *arg)
{ {
switch (mt) { switch (mt) {
case CARD_RESET: case CARD_RESET:
resetW6692(cs);
return (0); return (0);
case CARD_RELEASE: case CARD_RELEASE:
cs->writeW6692(cs, W_IMASK, 0xff);
release_region(cs->hw.w6692.iobase, 256); release_region(cs->hw.w6692.iobase, 256);
if (cs->subtyp == W6692_USR) {
cs->writeW6692(cs, W_XDATA, 0x04);
}
return (0); return (0);
case CARD_INIT: case CARD_INIT:
initW6692(cs, 3); initW6692(cs, 3);
...@@ -988,6 +1013,7 @@ setup_w6692(struct IsdnCard *card) ...@@ -988,6 +1013,7 @@ setup_w6692(struct IsdnCard *card)
if (dev_w6692) { if (dev_w6692) {
if (pci_enable_device(dev_w6692)) if (pci_enable_device(dev_w6692))
continue; continue;
cs->subtyp = id_idx;
break; break;
} }
id_idx++; id_idx++;
...@@ -998,6 +1024,13 @@ setup_w6692(struct IsdnCard *card) ...@@ -998,6 +1024,13 @@ setup_w6692(struct IsdnCard *card)
/* I think address 0 is allways the configuration area */ /* I think address 0 is allways the configuration area */
/* and address 1 is the real IO space KKe 03.09.99 */ /* and address 1 is the real IO space KKe 03.09.99 */
pci_ioaddr = pci_resource_start(dev_w6692, 1); pci_ioaddr = pci_resource_start(dev_w6692, 1);
/* USR ISDN PCI card TA need some special handling */
if (cs->subtyp == W6692_WINBOND) {
if ((W6692_SV_USR == dev_w6692->subsystem_vendor) &&
(W6692_SD_USR == dev_w6692->subsystem_device)) {
cs->subtyp = W6692_USR;
}
}
} }
if (!found) { if (!found) {
printk(KERN_WARNING "W6692: No PCI card found\n"); printk(KERN_WARNING "W6692: No PCI card found\n");
...@@ -1014,18 +1047,18 @@ setup_w6692(struct IsdnCard *card) ...@@ -1014,18 +1047,18 @@ setup_w6692(struct IsdnCard *card)
} }
cs->hw.w6692.iobase = pci_ioaddr; cs->hw.w6692.iobase = pci_ioaddr;
printk(KERN_INFO "Found: %s %s, I/O base: 0x%x, irq: %d\n", printk(KERN_INFO "Found: %s %s, I/O base: 0x%x, irq: %d\n",
id_list[id_idx].vendor_name, id_list[id_idx].card_name, id_list[cs->subtyp].vendor_name, id_list[cs->subtyp].card_name,
pci_ioaddr, dev_w6692->irq); pci_ioaddr, pci_irq);
if (check_region((cs->hw.w6692.iobase), 256)) { if (check_region((cs->hw.w6692.iobase), 256)) {
printk(KERN_WARNING printk(KERN_WARNING
"HiSax: %s I/O ports %x-%x already in use\n", "HiSax: %s I/O ports %x-%x already in use\n",
id_list[id_idx].card_name, id_list[cs->subtyp].card_name,
cs->hw.w6692.iobase, cs->hw.w6692.iobase,
cs->hw.w6692.iobase + 255); cs->hw.w6692.iobase + 255);
return (0); return (0);
} else { } else {
request_region(cs->hw.w6692.iobase, 256, request_region(cs->hw.w6692.iobase, 256,
id_list[id_idx].card_name); id_list[cs->subtyp].card_name);
} }
#else #else
printk(KERN_WARNING "HiSax: W6692 and NO_PCI_BIOS\n"); printk(KERN_WARNING "HiSax: W6692 and NO_PCI_BIOS\n");
...@@ -1035,7 +1068,7 @@ setup_w6692(struct IsdnCard *card) ...@@ -1035,7 +1068,7 @@ setup_w6692(struct IsdnCard *card)
printk(KERN_INFO printk(KERN_INFO
"HiSax: %s config irq:%d I/O:%x\n", "HiSax: %s config irq:%d I/O:%x\n",
id_list[id_idx].card_name, cs->irq, id_list[cs->subtyp].card_name, cs->irq,
cs->hw.w6692.iobase); cs->hw.w6692.iobase);
cs->readW6692 = &ReadW6692; cs->readW6692 = &ReadW6692;
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment