linux/drivers/isdn/hisax/config.c
<<
>>
Prefs
   1/* $Id: config.c,v 2.84.2.5 2004/02/11 13:21:33 keil Exp $
   2 *
   3 * Author       Karsten Keil
   4 * Copyright    by Karsten Keil      <keil@isdn4linux.de>
   5 *              by Kai Germaschewski <kai.germaschewski@gmx.de>
   6 *
   7 * This software may be used and distributed according to the terms
   8 * of the GNU General Public License, incorporated herein by reference.
   9 *
  10 * For changes and modifications please read
  11 * Documentation/isdn/HiSax.cert
  12 *
  13 * based on the teles driver from Jan den Ouden
  14 *
  15 */
  16
  17#include <linux/types.h>
  18#include <linux/stddef.h>
  19#include <linux/timer.h>
  20#include <linux/init.h>
  21#include "hisax.h"
  22#include <linux/module.h>
  23#include <linux/kernel_stat.h>
  24#include <linux/workqueue.h>
  25#include <linux/interrupt.h>
  26#include <linux/slab.h>
  27#define HISAX_STATUS_BUFSIZE 4096
  28
  29/*
  30 * This structure array contains one entry per card. An entry looks
  31 * like this:
  32 *
  33 * { type, protocol, p0, p1, p2, NULL }
  34 *
  35 * type
  36 *    1 Teles 16.0       p0=irq p1=membase p2=iobase
  37 *    2 Teles  8.0       p0=irq p1=membase
  38 *    3 Teles 16.3       p0=irq p1=iobase
  39 *    4 Creatix PNP      p0=irq p1=IO0 (ISAC)  p2=IO1 (HSCX)
  40 *    5 AVM A1 (Fritz)   p0=irq p1=iobase
  41 *    6 ELSA PC          [p0=iobase] or nothing (autodetect)
  42 *    7 ELSA Quickstep   p0=irq p1=iobase
  43 *    8 Teles PCMCIA     p0=irq p1=iobase
  44 *    9 ITK ix1-micro    p0=irq p1=iobase
  45 *   10 ELSA PCMCIA      p0=irq p1=iobase
  46 *   11 Eicon.Diehl Diva p0=irq p1=iobase
  47 *   12 Asuscom ISDNLink p0=irq p1=iobase
  48 *   13 Teleint          p0=irq p1=iobase
  49 *   14 Teles 16.3c      p0=irq p1=iobase
  50 *   15 Sedlbauer speed  p0=irq p1=iobase
  51 *   15 Sedlbauer PC/104        p0=irq p1=iobase
  52 *   15 Sedlbauer speed pci     no parameter
  53 *   16 USR Sportster internal  p0=irq  p1=iobase
  54 *   17 MIC card                p0=irq  p1=iobase
  55 *   18 ELSA Quickstep 1000PCI  no parameter
  56 *   19 Compaq ISDN S0 ISA card p0=irq  p1=IO0 (HSCX)  p2=IO1 (ISAC) p3=IO2
  57 *   20 Travers Technologies NETjet-S PCI card
  58 *   21 TELES PCI               no parameter
  59 *   22 Sedlbauer Speed Star    p0=irq p1=iobase
  60 *   23 reserved
  61 *   24 Dr Neuhaus Niccy PnP/PCI card p0=irq p1=IO0 p2=IO1 (PnP only)
  62 *   25 Teles S0Box             p0=irq p1=iobase (from isapnp setup)
  63 *   26 AVM A1 PCMCIA (Fritz)   p0=irq p1=iobase
  64 *   27 AVM PnP/PCI             p0=irq p1=iobase (PCI no parameter)
  65 *   28 Sedlbauer Speed Fax+    p0=irq p1=iobase (from isapnp setup)
  66 *   29 Siemens I-Surf          p0=irq p1=iobase p2=memory (from isapnp setup)
  67 *   30 ACER P10                p0=irq p1=iobase (from isapnp setup)
  68 *   31 HST Saphir              p0=irq  p1=iobase
  69 *   32 Telekom A4T             none
  70 *   33 Scitel Quadro           p0=subcontroller (4*S0, subctrl 1...4)
  71 *   34 Gazel ISDN cards
  72 *   35 HFC 2BDS0 PCI           none
  73 *   36 Winbond 6692 PCI        none
  74 *   37 HFC 2BDS0 S+/SP         p0=irq p1=iobase
  75 *   38 Travers Technologies NETspider-U PCI card
  76 *   39 HFC 2BDS0-SP PCMCIA     p0=irq p1=iobase
  77 *   40 hotplug interface
  78 *   41 Formula-n enter:now ISDN PCI a/b   none
  79 *
  80 * protocol can be either ISDN_PTYPE_EURO or ISDN_PTYPE_1TR6 or ISDN_PTYPE_NI1
  81 *
  82 *
  83 */
  84
  85const char *CardType[] = {
  86        "No Card", "Teles 16.0", "Teles 8.0", "Teles 16.3",
  87        "Creatix/Teles PnP", "AVM A1", "Elsa ML", "Elsa Quickstep",
  88        "Teles PCMCIA", "ITK ix1-micro Rev.2", "Elsa PCMCIA",
  89        "Eicon.Diehl Diva", "ISDNLink", "TeleInt", "Teles 16.3c",
  90        "Sedlbauer Speed Card", "USR Sportster", "ith mic Linux",
  91        "Elsa PCI", "Compaq ISA", "NETjet-S", "Teles PCI",
  92        "Sedlbauer Speed Star (PCMCIA)", "AMD 7930", "NICCY", "S0Box",
  93        "AVM A1 (PCMCIA)", "AVM Fritz PnP/PCI", "Sedlbauer Speed Fax +",
  94        "Siemens I-Surf", "Acer P10", "HST Saphir", "Telekom A4T",
  95        "Scitel Quadro", "Gazel", "HFC 2BDS0 PCI", "Winbond 6692",
  96        "HFC 2BDS0 SX", "NETspider-U", "HFC-2BDS0-SP PCMCIA",
  97        "Hotplug", "Formula-n enter:now PCI a/b",
  98};
  99
 100#ifdef CONFIG_HISAX_ELSA
 101#define DEFAULT_CARD ISDN_CTYPE_ELSA
 102#define DEFAULT_CFG {0, 0, 0, 0}
 103#endif
 104
 105#ifdef CONFIG_HISAX_AVM_A1
 106#undef DEFAULT_CARD
 107#undef DEFAULT_CFG
 108#define DEFAULT_CARD ISDN_CTYPE_A1
 109#define DEFAULT_CFG {10, 0x340, 0, 0}
 110#endif
 111
 112#ifdef CONFIG_HISAX_AVM_A1_PCMCIA
 113#undef DEFAULT_CARD
 114#undef DEFAULT_CFG
 115#define DEFAULT_CARD ISDN_CTYPE_A1_PCMCIA
 116#define DEFAULT_CFG {11, 0x170, 0, 0}
 117#endif
 118
 119#ifdef CONFIG_HISAX_FRITZPCI
 120#undef DEFAULT_CARD
 121#undef DEFAULT_CFG
 122#define DEFAULT_CARD ISDN_CTYPE_FRITZPCI
 123#define DEFAULT_CFG {0, 0, 0, 0}
 124#endif
 125
 126#ifdef CONFIG_HISAX_16_3
 127#undef DEFAULT_CARD
 128#undef DEFAULT_CFG
 129#define DEFAULT_CARD ISDN_CTYPE_16_3
 130#define DEFAULT_CFG {15, 0x180, 0, 0}
 131#endif
 132
 133#ifdef CONFIG_HISAX_S0BOX
 134#undef DEFAULT_CARD
 135#undef DEFAULT_CFG
 136#define DEFAULT_CARD ISDN_CTYPE_S0BOX
 137#define DEFAULT_CFG {7, 0x378, 0, 0}
 138#endif
 139
 140#ifdef CONFIG_HISAX_16_0
 141#undef DEFAULT_CARD
 142#undef DEFAULT_CFG
 143#define DEFAULT_CARD ISDN_CTYPE_16_0
 144#define DEFAULT_CFG {15, 0xd0000, 0xd80, 0}
 145#endif
 146
 147#ifdef CONFIG_HISAX_TELESPCI
 148#undef DEFAULT_CARD
 149#undef DEFAULT_CFG
 150#define DEFAULT_CARD ISDN_CTYPE_TELESPCI
 151#define DEFAULT_CFG {0, 0, 0, 0}
 152#endif
 153
 154#ifdef CONFIG_HISAX_IX1MICROR2
 155#undef DEFAULT_CARD
 156#undef DEFAULT_CFG
 157#define DEFAULT_CARD ISDN_CTYPE_IX1MICROR2
 158#define DEFAULT_CFG {5, 0x390, 0, 0}
 159#endif
 160
 161#ifdef CONFIG_HISAX_DIEHLDIVA
 162#undef DEFAULT_CARD
 163#undef DEFAULT_CFG
 164#define DEFAULT_CARD ISDN_CTYPE_DIEHLDIVA
 165#define DEFAULT_CFG {0, 0x0, 0, 0}
 166#endif
 167
 168#ifdef CONFIG_HISAX_ASUSCOM
 169#undef DEFAULT_CARD
 170#undef DEFAULT_CFG
 171#define DEFAULT_CARD ISDN_CTYPE_ASUSCOM
 172#define DEFAULT_CFG {5, 0x200, 0, 0}
 173#endif
 174
 175#ifdef CONFIG_HISAX_TELEINT
 176#undef DEFAULT_CARD
 177#undef DEFAULT_CFG
 178#define DEFAULT_CARD ISDN_CTYPE_TELEINT
 179#define DEFAULT_CFG {5, 0x300, 0, 0}
 180#endif
 181
 182#ifdef CONFIG_HISAX_SEDLBAUER
 183#undef DEFAULT_CARD
 184#undef DEFAULT_CFG
 185#define DEFAULT_CARD ISDN_CTYPE_SEDLBAUER
 186#define DEFAULT_CFG {11, 0x270, 0, 0}
 187#endif
 188
 189#ifdef CONFIG_HISAX_SPORTSTER
 190#undef DEFAULT_CARD
 191#undef DEFAULT_CFG
 192#define DEFAULT_CARD ISDN_CTYPE_SPORTSTER
 193#define DEFAULT_CFG {7, 0x268, 0, 0}
 194#endif
 195
 196#ifdef CONFIG_HISAX_MIC
 197#undef DEFAULT_CARD
 198#undef DEFAULT_CFG
 199#define DEFAULT_CARD ISDN_CTYPE_MIC
 200#define DEFAULT_CFG {12, 0x3e0, 0, 0}
 201#endif
 202
 203#ifdef CONFIG_HISAX_NETJET
 204#undef DEFAULT_CARD
 205#undef DEFAULT_CFG
 206#define DEFAULT_CARD ISDN_CTYPE_NETJET_S
 207#define DEFAULT_CFG {0, 0, 0, 0}
 208#endif
 209
 210#ifdef CONFIG_HISAX_HFCS
 211#undef DEFAULT_CARD
 212#undef DEFAULT_CFG
 213#define DEFAULT_CARD ISDN_CTYPE_TELES3C
 214#define DEFAULT_CFG {5, 0x500, 0, 0}
 215#endif
 216
 217#ifdef CONFIG_HISAX_HFC_PCI
 218#undef DEFAULT_CARD
 219#undef DEFAULT_CFG
 220#define DEFAULT_CARD ISDN_CTYPE_HFC_PCI
 221#define DEFAULT_CFG {0, 0, 0, 0}
 222#endif
 223
 224#ifdef CONFIG_HISAX_HFC_SX
 225#undef DEFAULT_CARD
 226#undef DEFAULT_CFG
 227#define DEFAULT_CARD ISDN_CTYPE_HFC_SX
 228#define DEFAULT_CFG {5, 0x2E0, 0, 0}
 229#endif
 230
 231#ifdef CONFIG_HISAX_NICCY
 232#undef DEFAULT_CARD
 233#undef DEFAULT_CFG
 234#define DEFAULT_CARD ISDN_CTYPE_NICCY
 235#define DEFAULT_CFG {0, 0x0, 0, 0}
 236#endif
 237
 238#ifdef CONFIG_HISAX_ISURF
 239#undef DEFAULT_CARD
 240#undef DEFAULT_CFG
 241#define DEFAULT_CARD ISDN_CTYPE_ISURF
 242#define DEFAULT_CFG {5, 0x100, 0xc8000, 0}
 243#endif
 244
 245#ifdef CONFIG_HISAX_HSTSAPHIR
 246#undef DEFAULT_CARD
 247#undef DEFAULT_CFG
 248#define DEFAULT_CARD ISDN_CTYPE_HSTSAPHIR
 249#define DEFAULT_CFG {5, 0x250, 0, 0}
 250#endif
 251
 252#ifdef CONFIG_HISAX_BKM_A4T
 253#undef DEFAULT_CARD
 254#undef DEFAULT_CFG
 255#define DEFAULT_CARD ISDN_CTYPE_BKM_A4T
 256#define DEFAULT_CFG {0, 0x0, 0, 0}
 257#endif
 258
 259#ifdef CONFIG_HISAX_SCT_QUADRO
 260#undef DEFAULT_CARD
 261#undef DEFAULT_CFG
 262#define DEFAULT_CARD ISDN_CTYPE_SCT_QUADRO
 263#define DEFAULT_CFG {1, 0x0, 0, 0}
 264#endif
 265
 266#ifdef CONFIG_HISAX_GAZEL
 267#undef DEFAULT_CARD
 268#undef DEFAULT_CFG
 269#define DEFAULT_CARD ISDN_CTYPE_GAZEL
 270#define DEFAULT_CFG {15, 0x180, 0, 0}
 271#endif
 272
 273#ifdef CONFIG_HISAX_W6692
 274#undef DEFAULT_CARD
 275#undef DEFAULT_CFG
 276#define DEFAULT_CARD ISDN_CTYPE_W6692
 277#define DEFAULT_CFG {0, 0, 0, 0}
 278#endif
 279
 280#ifdef CONFIG_HISAX_NETJET_U
 281#undef DEFAULT_CARD
 282#undef DEFAULT_CFG
 283#define DEFAULT_CARD ISDN_CTYPE_NETJET_U
 284#define DEFAULT_CFG {0, 0, 0, 0}
 285#endif
 286
 287#ifdef CONFIG_HISAX_1TR6
 288#define DEFAULT_PROTO ISDN_PTYPE_1TR6
 289#define DEFAULT_PROTO_NAME "1TR6"
 290#endif
 291#ifdef CONFIG_HISAX_NI1
 292#undef DEFAULT_PROTO
 293#define DEFAULT_PROTO ISDN_PTYPE_NI1
 294#undef DEFAULT_PROTO_NAME
 295#define DEFAULT_PROTO_NAME "NI1"
 296#endif
 297#ifdef CONFIG_HISAX_EURO
 298#undef DEFAULT_PROTO
 299#define DEFAULT_PROTO ISDN_PTYPE_EURO
 300#undef DEFAULT_PROTO_NAME
 301#define DEFAULT_PROTO_NAME "EURO"
 302#endif
 303#ifndef DEFAULT_PROTO
 304#define DEFAULT_PROTO ISDN_PTYPE_UNKNOWN
 305#define DEFAULT_PROTO_NAME "UNKNOWN"
 306#endif
 307#ifndef DEFAULT_CARD
 308#define DEFAULT_CARD 0
 309#define DEFAULT_CFG {0, 0, 0, 0}
 310#endif
 311
 312#define FIRST_CARD {                            \
 313                DEFAULT_CARD,                   \
 314                        DEFAULT_PROTO,          \
 315                        DEFAULT_CFG,            \
 316                        NULL,                   \
 317                        }
 318
 319struct IsdnCard cards[HISAX_MAX_CARDS] = {
 320        FIRST_CARD,
 321};
 322
 323#define HISAX_IDSIZE (HISAX_MAX_CARDS * 8)
 324static char HiSaxID[HISAX_IDSIZE] = { 0, };
 325
 326static char *HiSax_id = HiSaxID;
 327#ifdef MODULE
 328/* Variables for insmod */
 329static int type[HISAX_MAX_CARDS] = { 0, };
 330static int protocol[HISAX_MAX_CARDS] = { 0, };
 331static int io[HISAX_MAX_CARDS] = { 0, };
 332#undef IO0_IO1
 333#ifdef CONFIG_HISAX_16_3
 334#define IO0_IO1
 335#endif
 336#ifdef CONFIG_HISAX_NICCY
 337#undef IO0_IO1
 338#define IO0_IO1
 339#endif
 340#ifdef IO0_IO1
 341static int io0[HISAX_MAX_CARDS] = { 0, };
 342static int io1[HISAX_MAX_CARDS] = { 0, };
 343#endif
 344static int irq[HISAX_MAX_CARDS] = { 0, };
 345static int mem[HISAX_MAX_CARDS] = { 0, };
 346static char *id = HiSaxID;
 347
 348MODULE_DESCRIPTION("ISDN4Linux: Driver for passive ISDN cards");
 349MODULE_AUTHOR("Karsten Keil");
 350MODULE_LICENSE("GPL");
 351module_param_array(type, int, NULL, 0);
 352module_param_array(protocol, int, NULL, 0);
 353module_param_hw_array(io, int, ioport, NULL, 0);
 354module_param_hw_array(irq, int, irq, NULL, 0);
 355module_param_hw_array(mem, int, iomem, NULL, 0);
 356module_param(id, charp, 0);
 357#ifdef IO0_IO1
 358module_param_hw_array(io0, int, ioport, NULL, 0);
 359module_param_hw_array(io1, int, ioport, NULL, 0);
 360#endif
 361#endif /* MODULE */
 362
 363int nrcards;
 364
 365char *HiSax_getrev(const char *revision)
 366{
 367        char *rev;
 368        char *p;
 369
 370        if ((p = strchr(revision, ':'))) {
 371                rev = p + 2;
 372                p = strchr(rev, '$');
 373                *--p = 0;
 374        } else
 375                rev = "???";
 376        return rev;
 377}
 378
 379static void __init HiSaxVersion(void)
 380{
 381        char tmp[64];
 382
 383        printk(KERN_INFO "HiSax: Linux Driver for passive ISDN cards\n");
 384#ifdef MODULE
 385        printk(KERN_INFO "HiSax: Version 3.5 (module)\n");
 386#else
 387        printk(KERN_INFO "HiSax: Version 3.5 (kernel)\n");
 388#endif
 389        strcpy(tmp, l1_revision);
 390        printk(KERN_INFO "HiSax: Layer1 Revision %s\n", HiSax_getrev(tmp));
 391        strcpy(tmp, l2_revision);
 392        printk(KERN_INFO "HiSax: Layer2 Revision %s\n", HiSax_getrev(tmp));
 393        strcpy(tmp, tei_revision);
 394        printk(KERN_INFO "HiSax: TeiMgr Revision %s\n", HiSax_getrev(tmp));
 395        strcpy(tmp, l3_revision);
 396        printk(KERN_INFO "HiSax: Layer3 Revision %s\n", HiSax_getrev(tmp));
 397        strcpy(tmp, lli_revision);
 398        printk(KERN_INFO "HiSax: LinkLayer Revision %s\n",
 399               HiSax_getrev(tmp));
 400}
 401
 402#ifndef MODULE
 403#define MAX_ARG (HISAX_MAX_CARDS * 5)
 404static int __init HiSax_setup(char *line)
 405{
 406        int i, j, argc;
 407        int ints[MAX_ARG + 1];
 408        char *str;
 409
 410        str = get_options(line, MAX_ARG, ints);
 411        argc = ints[0];
 412        printk(KERN_DEBUG "HiSax_setup: argc(%d) str(%s)\n", argc, str);
 413        i = 0;
 414        j = 1;
 415        while (argc && (i < HISAX_MAX_CARDS)) {
 416                cards[i].protocol = DEFAULT_PROTO;
 417                if (argc) {
 418                        cards[i].typ = ints[j];
 419                        j++;
 420                        argc--;
 421                }
 422                if (argc) {
 423                        cards[i].protocol = ints[j];
 424                        j++;
 425                        argc--;
 426                }
 427                if (argc) {
 428                        cards[i].para[0] = ints[j];
 429                        j++;
 430                        argc--;
 431                }
 432                if (argc) {
 433                        cards[i].para[1] = ints[j];
 434                        j++;
 435                        argc--;
 436                }
 437                if (argc) {
 438                        cards[i].para[2] = ints[j];
 439                        j++;
 440                        argc--;
 441                }
 442                i++;
 443        }
 444        if (str && *str) {
 445                if (strlen(str) < HISAX_IDSIZE)
 446                        strcpy(HiSaxID, str);
 447                else
 448                        printk(KERN_WARNING "HiSax: ID too long!");
 449        } else
 450                strcpy(HiSaxID, "HiSax");
 451
 452        HiSax_id = HiSaxID;
 453        return 1;
 454}
 455
 456__setup("hisax=", HiSax_setup);
 457#endif /* MODULES */
 458
 459#if CARD_TELES0
 460extern int setup_teles0(struct IsdnCard *card);
 461#endif
 462
 463#if CARD_TELES3
 464extern int setup_teles3(struct IsdnCard *card);
 465#endif
 466
 467#if CARD_S0BOX
 468extern int setup_s0box(struct IsdnCard *card);
 469#endif
 470
 471#if CARD_TELESPCI
 472extern int setup_telespci(struct IsdnCard *card);
 473#endif
 474
 475#if CARD_AVM_A1
 476extern int setup_avm_a1(struct IsdnCard *card);
 477#endif
 478
 479#if CARD_AVM_A1_PCMCIA
 480extern int setup_avm_a1_pcmcia(struct IsdnCard *card);
 481#endif
 482
 483#if CARD_FRITZPCI
 484extern int setup_avm_pcipnp(struct IsdnCard *card);
 485#endif
 486
 487#if CARD_ELSA
 488extern int setup_elsa(struct IsdnCard *card);
 489#endif
 490
 491#if CARD_IX1MICROR2
 492extern int setup_ix1micro(struct IsdnCard *card);
 493#endif
 494
 495#if CARD_DIEHLDIVA
 496extern int setup_diva(struct IsdnCard *card);
 497#endif
 498
 499#if CARD_ASUSCOM
 500extern int setup_asuscom(struct IsdnCard *card);
 501#endif
 502
 503#if CARD_TELEINT
 504extern int setup_TeleInt(struct IsdnCard *card);
 505#endif
 506
 507#if CARD_SEDLBAUER
 508extern int setup_sedlbauer(struct IsdnCard *card);
 509#endif
 510
 511#if CARD_SPORTSTER
 512extern int setup_sportster(struct IsdnCard *card);
 513#endif
 514
 515#if CARD_MIC
 516extern int setup_mic(struct IsdnCard *card);
 517#endif
 518
 519#if CARD_NETJET_S
 520extern int setup_netjet_s(struct IsdnCard *card);
 521#endif
 522
 523#if CARD_HFCS
 524extern int setup_hfcs(struct IsdnCard *card);
 525#endif
 526
 527#if CARD_HFC_PCI
 528extern int setup_hfcpci(struct IsdnCard *card);
 529#endif
 530
 531#if CARD_HFC_SX
 532extern int setup_hfcsx(struct IsdnCard *card);
 533#endif
 534
 535#if CARD_NICCY
 536extern int setup_niccy(struct IsdnCard *card);
 537#endif
 538
 539#if CARD_ISURF
 540extern int setup_isurf(struct IsdnCard *card);
 541#endif
 542
 543#if CARD_HSTSAPHIR
 544extern int setup_saphir(struct IsdnCard *card);
 545#endif
 546
 547#if CARD_BKM_A4T
 548extern int setup_bkm_a4t(struct IsdnCard *card);
 549#endif
 550
 551#if CARD_SCT_QUADRO
 552extern int setup_sct_quadro(struct IsdnCard *card);
 553#endif
 554
 555#if CARD_GAZEL
 556extern int setup_gazel(struct IsdnCard *card);
 557#endif
 558
 559#if CARD_W6692
 560extern int setup_w6692(struct IsdnCard *card);
 561#endif
 562
 563#if CARD_NETJET_U
 564extern int setup_netjet_u(struct IsdnCard *card);
 565#endif
 566
 567#if CARD_FN_ENTERNOW_PCI
 568extern int setup_enternow_pci(struct IsdnCard *card);
 569#endif
 570
 571/*
 572 * Find card with given driverId
 573 */
 574static inline struct IsdnCardState *hisax_findcard(int driverid)
 575{
 576        int i;
 577
 578        for (i = 0; i < nrcards; i++)
 579                if (cards[i].cs)
 580                        if (cards[i].cs->myid == driverid)
 581                                return cards[i].cs;
 582        return NULL;
 583}
 584
 585/*
 586 * Find card with given card number
 587 */
 588#if 0
 589struct IsdnCardState *hisax_get_card(int cardnr)
 590{
 591        if ((cardnr <= nrcards) && (cardnr > 0))
 592                if (cards[cardnr - 1].cs)
 593                        return cards[cardnr - 1].cs;
 594        return NULL;
 595}
 596#endif  /*  0  */
 597
 598static int HiSax_readstatus(u_char __user *buf, int len, int id, int channel)
 599{
 600        int count, cnt;
 601        u_char __user *p = buf;
 602        struct IsdnCardState *cs = hisax_findcard(id);
 603
 604        if (cs) {
 605                if (len > HISAX_STATUS_BUFSIZE) {
 606                        printk(KERN_WARNING
 607                               "HiSax: status overflow readstat %d/%d\n",
 608                               len, HISAX_STATUS_BUFSIZE);
 609                }
 610                count = cs->status_end - cs->status_read + 1;
 611                if (count >= len)
 612                        count = len;
 613                if (copy_to_user(p, cs->status_read, count))
 614                        return -EFAULT;
 615                cs->status_read += count;
 616                if (cs->status_read > cs->status_end)
 617                        cs->status_read = cs->status_buf;
 618                p += count;
 619                count = len - count;
 620                while (count) {
 621                        if (count > HISAX_STATUS_BUFSIZE)
 622                                cnt = HISAX_STATUS_BUFSIZE;
 623                        else
 624                                cnt = count;
 625                        if (copy_to_user(p, cs->status_read, cnt))
 626                                return -EFAULT;
 627                        p += cnt;
 628                        cs->status_read += cnt % HISAX_STATUS_BUFSIZE;
 629                        count -= cnt;
 630                }
 631                return len;
 632        } else {
 633                printk(KERN_ERR
 634                       "HiSax: if_readstatus called with invalid driverId!\n");
 635                return -ENODEV;
 636        }
 637}
 638
 639int jiftime(char *s, long mark)
 640{
 641        s += 8;
 642
 643        *s-- = '\0';
 644        *s-- = mark % 10 + '0';
 645        mark /= 10;
 646        *s-- = mark % 10 + '0';
 647        mark /= 10;
 648        *s-- = '.';
 649        *s-- = mark % 10 + '0';
 650        mark /= 10;
 651        *s-- = mark % 6 + '0';
 652        mark /= 6;
 653        *s-- = ':';
 654        *s-- = mark % 10 + '0';
 655        mark /= 10;
 656        *s-- = mark % 10 + '0';
 657        return 8;
 658}
 659
 660static u_char tmpbuf[HISAX_STATUS_BUFSIZE];
 661
 662void VHiSax_putstatus(struct IsdnCardState *cs, char *head, const char *fmt,
 663                      va_list args)
 664{
 665        /* if head == NULL the fmt contains the full info */
 666
 667        u_long          flags;
 668        int             count, i;
 669        u_char          *p;
 670        isdn_ctrl       ic;
 671        int             len;
 672        const u_char    *data;
 673
 674        if (!cs) {
 675                printk(KERN_WARNING "HiSax: No CardStatus for message");
 676                return;
 677        }
 678        spin_lock_irqsave(&cs->statlock, flags);
 679        if (head) {
 680                p = tmpbuf;
 681                p += jiftime(p, jiffies);
 682                p += sprintf(p, " %s", head);
 683                p += vsprintf(p, fmt, args);
 684                *p++ = '\n';
 685                *p = 0;
 686                len = p - tmpbuf;
 687                data = tmpbuf;
 688        } else {
 689                data = fmt;
 690                len = strlen(fmt);
 691        }
 692        if (len > HISAX_STATUS_BUFSIZE) {
 693                spin_unlock_irqrestore(&cs->statlock, flags);
 694                printk(KERN_WARNING "HiSax: status overflow %d/%d\n",
 695                       len, HISAX_STATUS_BUFSIZE);
 696                return;
 697        }
 698        count = len;
 699        i = cs->status_end - cs->status_write + 1;
 700        if (i >= len)
 701                i = len;
 702        len -= i;
 703        memcpy(cs->status_write, data, i);
 704        cs->status_write += i;
 705        if (cs->status_write > cs->status_end)
 706                cs->status_write = cs->status_buf;
 707        if (len) {
 708                memcpy(cs->status_write, data + i, len);
 709                cs->status_write += len;
 710        }
 711#ifdef KERNELSTACK_DEBUG
 712        i = (ulong) & len - current->kernel_stack_page;
 713        sprintf(tmpbuf, "kstack %s %lx use %ld\n", current->comm,
 714                current->kernel_stack_page, i);
 715        len = strlen(tmpbuf);
 716        for (p = tmpbuf, i = len; i > 0; i--, p++) {
 717                *cs->status_write++ = *p;
 718                if (cs->status_write > cs->status_end)
 719                        cs->status_write = cs->status_buf;
 720                count++;
 721        }
 722#endif
 723        spin_unlock_irqrestore(&cs->statlock, flags);
 724        if (count) {
 725                ic.command = ISDN_STAT_STAVAIL;
 726                ic.driver = cs->myid;
 727                ic.arg = count;
 728                cs->iif.statcallb(&ic);
 729        }
 730}
 731
 732void HiSax_putstatus(struct IsdnCardState *cs, char *head, const char *fmt, ...)
 733{
 734        va_list args;
 735
 736        va_start(args, fmt);
 737        VHiSax_putstatus(cs, head, fmt, args);
 738        va_end(args);
 739}
 740
 741int ll_run(struct IsdnCardState *cs, int addfeatures)
 742{
 743        isdn_ctrl ic;
 744
 745        ic.driver = cs->myid;
 746        ic.command = ISDN_STAT_RUN;
 747        cs->iif.features |= addfeatures;
 748        cs->iif.statcallb(&ic);
 749        return 0;
 750}
 751
 752static void ll_stop(struct IsdnCardState *cs)
 753{
 754        isdn_ctrl ic;
 755
 756        ic.command = ISDN_STAT_STOP;
 757        ic.driver = cs->myid;
 758        cs->iif.statcallb(&ic);
 759        //      CallcFreeChan(cs);
 760}
 761
 762static void ll_unload(struct IsdnCardState *cs)
 763{
 764        isdn_ctrl ic;
 765
 766        ic.command = ISDN_STAT_UNLOAD;
 767        ic.driver = cs->myid;
 768        cs->iif.statcallb(&ic);
 769        kfree(cs->status_buf);
 770        cs->status_read = NULL;
 771        cs->status_write = NULL;
 772        cs->status_end = NULL;
 773        kfree(cs->dlog);
 774        cs->dlog = NULL;
 775}
 776
 777static void closecard(int cardnr)
 778{
 779        struct IsdnCardState *csta = cards[cardnr].cs;
 780
 781        if (csta->bcs->BC_Close != NULL) {
 782                csta->bcs->BC_Close(csta->bcs + 1);
 783                csta->bcs->BC_Close(csta->bcs);
 784        }
 785
 786        skb_queue_purge(&csta->rq);
 787        skb_queue_purge(&csta->sq);
 788        kfree(csta->rcvbuf);
 789        csta->rcvbuf = NULL;
 790        if (csta->tx_skb) {
 791                dev_kfree_skb(csta->tx_skb);
 792                csta->tx_skb = NULL;
 793        }
 794        if (csta->DC_Close != NULL) {
 795                csta->DC_Close(csta);
 796        }
 797        if (csta->cardmsg)
 798                csta->cardmsg(csta, CARD_RELEASE, NULL);
 799        if (csta->dbusytimer.function != NULL) // FIXME?
 800                del_timer(&csta->dbusytimer);
 801        ll_unload(csta);
 802}
 803
 804static irqreturn_t card_irq(int intno, void *dev_id)
 805{
 806        struct IsdnCardState *cs = dev_id;
 807        irqreturn_t ret = cs->irq_func(intno, cs);
 808
 809        if (ret == IRQ_HANDLED)
 810                cs->irq_cnt++;
 811        return ret;
 812}
 813
 814static int init_card(struct IsdnCardState *cs)
 815{
 816        int     irq_cnt, cnt = 3, ret;
 817
 818        if (!cs->irq) {
 819                ret = cs->cardmsg(cs, CARD_INIT, NULL);
 820                return (ret);
 821        }
 822        irq_cnt = cs->irq_cnt = 0;
 823        printk(KERN_INFO "%s: IRQ %d count %d\n", CardType[cs->typ],
 824               cs->irq, irq_cnt);
 825        if (request_irq(cs->irq, card_irq, cs->irq_flags, "HiSax", cs)) {
 826                printk(KERN_WARNING "HiSax: couldn't get interrupt %d\n",
 827                       cs->irq);
 828                return 1;
 829        }
 830        while (cnt) {
 831                cs->cardmsg(cs, CARD_INIT, NULL);
 832                /* Timeout 10ms */
 833                msleep(10);
 834                printk(KERN_INFO "%s: IRQ %d count %d\n",
 835                       CardType[cs->typ], cs->irq, cs->irq_cnt);
 836                if (cs->irq_cnt == irq_cnt) {
 837                        printk(KERN_WARNING
 838                               "%s: IRQ(%d) getting no interrupts during init %d\n",
 839                               CardType[cs->typ], cs->irq, 4 - cnt);
 840                        if (cnt == 1) {
 841                                free_irq(cs->irq, cs);
 842                                return 2;
 843                        } else {
 844                                cs->cardmsg(cs, CARD_RESET, NULL);
 845                                cnt--;
 846                        }
 847                } else {
 848                        cs->cardmsg(cs, CARD_TEST, NULL);
 849                        return 0;
 850                }
 851        }
 852        return 3;
 853}
 854
 855static int hisax_cs_setup_card(struct IsdnCard *card)
 856{
 857        int ret;
 858
 859        switch (card->typ) {
 860#if CARD_TELES0
 861        case ISDN_CTYPE_16_0:
 862        case ISDN_CTYPE_8_0:
 863                ret = setup_teles0(card);
 864                break;
 865#endif
 866#if CARD_TELES3
 867        case ISDN_CTYPE_16_3:
 868        case ISDN_CTYPE_PNP:
 869        case ISDN_CTYPE_TELESPCMCIA:
 870        case ISDN_CTYPE_COMPAQ_ISA:
 871                ret = setup_teles3(card);
 872                break;
 873#endif
 874#if CARD_S0BOX
 875        case ISDN_CTYPE_S0BOX:
 876                ret = setup_s0box(card);
 877                break;
 878#endif
 879#if CARD_TELESPCI
 880        case ISDN_CTYPE_TELESPCI:
 881                ret = setup_telespci(card);
 882                break;
 883#endif
 884#if CARD_AVM_A1
 885        case ISDN_CTYPE_A1:
 886                ret = setup_avm_a1(card);
 887                break;
 888#endif
 889#if CARD_AVM_A1_PCMCIA
 890        case ISDN_CTYPE_A1_PCMCIA:
 891                ret = setup_avm_a1_pcmcia(card);
 892                break;
 893#endif
 894#if CARD_FRITZPCI
 895        case ISDN_CTYPE_FRITZPCI:
 896                ret = setup_avm_pcipnp(card);
 897                break;
 898#endif
 899#if CARD_ELSA
 900        case ISDN_CTYPE_ELSA:
 901        case ISDN_CTYPE_ELSA_PNP:
 902        case ISDN_CTYPE_ELSA_PCMCIA:
 903        case ISDN_CTYPE_ELSA_PCI:
 904                ret = setup_elsa(card);
 905                break;
 906#endif
 907#if CARD_IX1MICROR2
 908        case ISDN_CTYPE_IX1MICROR2:
 909                ret = setup_ix1micro(card);
 910                break;
 911#endif
 912#if CARD_DIEHLDIVA
 913        case ISDN_CTYPE_DIEHLDIVA:
 914                ret = setup_diva(card);
 915                break;
 916#endif
 917#if CARD_ASUSCOM
 918        case ISDN_CTYPE_ASUSCOM:
 919                ret = setup_asuscom(card);
 920                break;
 921#endif
 922#if CARD_TELEINT
 923        case ISDN_CTYPE_TELEINT:
 924                ret = setup_TeleInt(card);
 925                break;
 926#endif
 927#if CARD_SEDLBAUER
 928        case ISDN_CTYPE_SEDLBAUER:
 929        case ISDN_CTYPE_SEDLBAUER_PCMCIA:
 930        case ISDN_CTYPE_SEDLBAUER_FAX:
 931                ret = setup_sedlbauer(card);
 932                break;
 933#endif
 934#if CARD_SPORTSTER
 935        case ISDN_CTYPE_SPORTSTER:
 936                ret = setup_sportster(card);
 937                break;
 938#endif
 939#if CARD_MIC
 940        case ISDN_CTYPE_MIC:
 941                ret = setup_mic(card);
 942                break;
 943#endif
 944#if CARD_NETJET_S
 945        case ISDN_CTYPE_NETJET_S:
 946                ret = setup_netjet_s(card);
 947                break;
 948#endif
 949#if CARD_HFCS
 950        case ISDN_CTYPE_TELES3C:
 951        case ISDN_CTYPE_ACERP10:
 952                ret = setup_hfcs(card);
 953                break;
 954#endif
 955#if CARD_HFC_PCI
 956        case ISDN_CTYPE_HFC_PCI:
 957                ret = setup_hfcpci(card);
 958                break;
 959#endif
 960#if CARD_HFC_SX
 961        case ISDN_CTYPE_HFC_SX:
 962                ret = setup_hfcsx(card);
 963                break;
 964#endif
 965#if CARD_NICCY
 966        case ISDN_CTYPE_NICCY:
 967                ret = setup_niccy(card);
 968                break;
 969#endif
 970#if CARD_ISURF
 971        case ISDN_CTYPE_ISURF:
 972                ret = setup_isurf(card);
 973                break;
 974#endif
 975#if CARD_HSTSAPHIR
 976        case ISDN_CTYPE_HSTSAPHIR:
 977                ret = setup_saphir(card);
 978                break;
 979#endif
 980#if     CARD_BKM_A4T
 981        case ISDN_CTYPE_BKM_A4T:
 982                ret = setup_bkm_a4t(card);
 983                break;
 984#endif
 985#if     CARD_SCT_QUADRO
 986        case ISDN_CTYPE_SCT_QUADRO:
 987                ret = setup_sct_quadro(card);
 988                break;
 989#endif
 990#if CARD_GAZEL
 991        case ISDN_CTYPE_GAZEL:
 992                ret = setup_gazel(card);
 993                break;
 994#endif
 995#if CARD_W6692
 996        case ISDN_CTYPE_W6692:
 997                ret = setup_w6692(card);
 998                break;
 999#endif
1000#if CARD_NETJET_U
1001        case ISDN_CTYPE_NETJET_U:
1002                ret = setup_netjet_u(card);
1003                break;
1004#endif
1005#if CARD_FN_ENTERNOW_PCI
1006        case ISDN_CTYPE_ENTERNOW:
1007                ret = setup_enternow_pci(card);
1008                break;
1009#endif
1010        case ISDN_CTYPE_DYNAMIC:
1011                ret = 2;
1012                break;
1013        default:
1014                printk(KERN_WARNING
1015                       "HiSax: Support for %s Card not selected\n",
1016                       CardType[card->typ]);
1017                ret = 0;
1018                break;
1019        }
1020
1021        return ret;
1022}
1023
1024static int hisax_cs_new(int cardnr, char *id, struct IsdnCard *card,
1025                        struct IsdnCardState **cs_out, int *busy_flag,
1026                        struct module *lockowner)
1027{
1028        struct IsdnCardState *cs;
1029
1030        *cs_out = NULL;
1031
1032        cs = kzalloc(sizeof(struct IsdnCardState), GFP_ATOMIC);
1033        if (!cs) {
1034                printk(KERN_WARNING
1035                       "HiSax: No memory for IsdnCardState(card %d)\n",
1036                       cardnr + 1);
1037                goto out;
1038        }
1039        card->cs = cs;
1040        spin_lock_init(&cs->statlock);
1041        spin_lock_init(&cs->lock);
1042        cs->chanlimit = 2;      /* maximum B-channel number */
1043        cs->logecho = 0;        /* No echo logging */
1044        cs->cardnr = cardnr;
1045        cs->debug = L1_DEB_WARN;
1046        cs->HW_Flags = 0;
1047        cs->busy_flag = busy_flag;
1048        cs->irq_flags = I4L_IRQ_FLAG;
1049#if TEI_PER_CARD
1050        if (card->protocol == ISDN_PTYPE_NI1)
1051                test_and_set_bit(FLG_TWO_DCHAN, &cs->HW_Flags);
1052#else
1053        test_and_set_bit(FLG_TWO_DCHAN, &cs->HW_Flags);
1054#endif
1055        cs->protocol = card->protocol;
1056
1057        if (card->typ <= 0 || card->typ > ISDN_CTYPE_COUNT) {
1058                printk(KERN_WARNING
1059                       "HiSax: Card Type %d out of range\n", card->typ);
1060                goto outf_cs;
1061        }
1062        if (!(cs->dlog = kmalloc(MAX_DLOG_SPACE, GFP_ATOMIC))) {
1063                printk(KERN_WARNING
1064                       "HiSax: No memory for dlog(card %d)\n", cardnr + 1);
1065                goto outf_cs;
1066        }
1067        if (!(cs->status_buf = kmalloc(HISAX_STATUS_BUFSIZE, GFP_ATOMIC))) {
1068                printk(KERN_WARNING
1069                       "HiSax: No memory for status_buf(card %d)\n",
1070                       cardnr + 1);
1071                goto outf_dlog;
1072        }
1073        cs->stlist = NULL;
1074        cs->status_read = cs->status_buf;
1075        cs->status_write = cs->status_buf;
1076        cs->status_end = cs->status_buf + HISAX_STATUS_BUFSIZE - 1;
1077        cs->typ = card->typ;
1078#ifdef MODULE
1079        cs->iif.owner = lockowner;
1080#endif
1081        strcpy(cs->iif.id, id);
1082        cs->iif.channels = 2;
1083        cs->iif.maxbufsize = MAX_DATA_SIZE;
1084        cs->iif.hl_hdrlen = MAX_HEADER_LEN;
1085        cs->iif.features =
1086                ISDN_FEATURE_L2_X75I |
1087                ISDN_FEATURE_L2_HDLC |
1088                ISDN_FEATURE_L2_HDLC_56K |
1089                ISDN_FEATURE_L2_TRANS |
1090                ISDN_FEATURE_L3_TRANS |
1091#ifdef  CONFIG_HISAX_1TR6
1092                ISDN_FEATURE_P_1TR6 |
1093#endif
1094#ifdef  CONFIG_HISAX_EURO
1095                ISDN_FEATURE_P_EURO |
1096#endif
1097#ifdef  CONFIG_HISAX_NI1
1098                ISDN_FEATURE_P_NI1 |
1099#endif
1100                0;
1101
1102        cs->iif.command = HiSax_command;
1103        cs->iif.writecmd = NULL;
1104        cs->iif.writebuf_skb = HiSax_writebuf_skb;
1105        cs->iif.readstat = HiSax_readstatus;
1106        register_isdn(&cs->iif);
1107        cs->myid = cs->iif.channels;
1108
1109        *cs_out = cs;
1110        return 1;       /* success */
1111
1112outf_dlog:
1113        kfree(cs->dlog);
1114outf_cs:
1115        kfree(cs);
1116        card->cs = NULL;
1117out:
1118        return 0;       /* error */
1119}
1120
1121static int hisax_cs_setup(int cardnr, struct IsdnCard *card,
1122                          struct IsdnCardState *cs)
1123{
1124        int ret;
1125
1126        if (!(cs->rcvbuf = kmalloc(MAX_DFRAME_LEN_L1, GFP_ATOMIC))) {
1127                printk(KERN_WARNING "HiSax: No memory for isac rcvbuf\n");
1128                ll_unload(cs);
1129                goto outf_cs;
1130        }
1131        cs->rcvidx = 0;
1132        cs->tx_skb = NULL;
1133        cs->tx_cnt = 0;
1134        cs->event = 0;
1135
1136        skb_queue_head_init(&cs->rq);
1137        skb_queue_head_init(&cs->sq);
1138
1139        init_bcstate(cs, 0);
1140        init_bcstate(cs, 1);
1141
1142        /* init_card only handles interrupts which are not */
1143        /* used here for the loadable driver */
1144        switch (card->typ) {
1145        case ISDN_CTYPE_DYNAMIC:
1146                ret = 0;
1147                break;
1148        default:
1149                ret = init_card(cs);
1150                break;
1151        }
1152        if (ret) {
1153                closecard(cardnr);
1154                goto outf_cs;
1155        }
1156        init_tei(cs, cs->protocol);
1157        ret = CallcNewChan(cs);
1158        if (ret) {
1159                closecard(cardnr);
1160                goto outf_cs;
1161        }
1162        /* ISAR needs firmware download first */
1163        if (!test_bit(HW_ISAR, &cs->HW_Flags))
1164                ll_run(cs, 0);
1165
1166        return 1;
1167
1168outf_cs:
1169        kfree(cs);
1170        card->cs = NULL;
1171        return 0;
1172}
1173
1174static int checkcard(int cardnr, char *id, int *busy_flag,
1175                     struct module *lockowner, hisax_setup_func_t card_setup)
1176{
1177        int ret;
1178        struct IsdnCard *card = cards + cardnr;
1179        struct IsdnCardState *cs;
1180
1181        ret = hisax_cs_new(cardnr, id, card, &cs, busy_flag, lockowner);
1182        if (!ret)
1183                return 0;
1184
1185        printk(KERN_INFO
1186               "HiSax: Card %d Protocol %s Id=%s (%d)\n", cardnr + 1,
1187               (card->protocol == ISDN_PTYPE_1TR6) ? "1TR6" :
1188               (card->protocol == ISDN_PTYPE_EURO) ? "EDSS1" :
1189               (card->protocol == ISDN_PTYPE_LEASED) ? "LEASED" :
1190               (card->protocol == ISDN_PTYPE_NI1) ? "NI1" :
1191               "NONE", cs->iif.id, cs->myid);
1192
1193        ret = card_setup(card);
1194        if (!ret) {
1195                ll_unload(cs);
1196                goto outf_cs;
1197        }
1198
1199        ret = hisax_cs_setup(cardnr, card, cs);
1200        goto out;
1201
1202outf_cs:
1203        kfree(cs);
1204        card->cs = NULL;
1205out:
1206        return ret;
1207}
1208
1209static void HiSax_shiftcards(int idx)
1210{
1211        int i;
1212
1213        for (i = idx; i < (HISAX_MAX_CARDS - 1); i++)
1214                memcpy(&cards[i], &cards[i + 1], sizeof(cards[i]));
1215}
1216
1217static int __init HiSax_inithardware(int *busy_flag)
1218{
1219        int foundcards = 0;
1220        int i = 0;
1221        int t = ',';
1222        int flg = 0;
1223        char *id;
1224        char *next_id = HiSax_id;
1225        char ids[20];
1226
1227        if (strchr(HiSax_id, ','))
1228                t = ',';
1229        else if (strchr(HiSax_id, '%'))
1230                t = '%';
1231
1232        while (i < nrcards) {
1233                if (cards[i].typ < 1)
1234                        break;
1235                id = next_id;
1236                if ((next_id = strchr(id, t))) {
1237                        *next_id++ = 0;
1238                        strcpy(ids, id);
1239                        flg = i + 1;
1240                } else {
1241                        next_id = id;
1242                        if (flg >= i)
1243                                strcpy(ids, id);
1244                        else
1245                                sprintf(ids, "%s%d", id, i);
1246                }
1247                if (checkcard(i, ids, busy_flag, THIS_MODULE,
1248                              hisax_cs_setup_card)) {
1249                        foundcards++;
1250                        i++;
1251                } else {
1252                        /* make sure we don't oops the module */
1253                        if (cards[i].typ > 0 && cards[i].typ <= ISDN_CTYPE_COUNT) {
1254                                printk(KERN_WARNING
1255                                       "HiSax: Card %s not installed !\n",
1256                                       CardType[cards[i].typ]);
1257                        }
1258                        HiSax_shiftcards(i);
1259                        nrcards--;
1260                }
1261        }
1262        return foundcards;
1263}
1264
1265void HiSax_closecard(int cardnr)
1266{
1267        int i, last = nrcards - 1;
1268
1269        if (cardnr > last || cardnr < 0)
1270                return;
1271        if (cards[cardnr].cs) {
1272                ll_stop(cards[cardnr].cs);
1273                release_tei(cards[cardnr].cs);
1274                CallcFreeChan(cards[cardnr].cs);
1275
1276                closecard(cardnr);
1277                if (cards[cardnr].cs->irq)
1278                        free_irq(cards[cardnr].cs->irq, cards[cardnr].cs);
1279                kfree((void *) cards[cardnr].cs);
1280                cards[cardnr].cs = NULL;
1281        }
1282        i = cardnr;
1283        while (i <= last) {
1284                cards[i] = cards[i + 1];
1285                i++;
1286        }
1287        nrcards--;
1288}
1289
1290void HiSax_reportcard(int cardnr, int sel)
1291{
1292        struct IsdnCardState *cs = cards[cardnr].cs;
1293
1294        printk(KERN_DEBUG "HiSax: reportcard No %d\n", cardnr + 1);
1295        printk(KERN_DEBUG "HiSax: Type %s\n", CardType[cs->typ]);
1296        printk(KERN_DEBUG "HiSax: debuglevel %x\n", cs->debug);
1297        printk(KERN_DEBUG "HiSax: HiSax_reportcard address 0x%lX\n",
1298               (ulong) & HiSax_reportcard);
1299        printk(KERN_DEBUG "HiSax: cs 0x%lX\n", (ulong) cs);
1300        printk(KERN_DEBUG "HiSax: HW_Flags %lx bc0 flg %lx bc1 flg %lx\n",
1301               cs->HW_Flags, cs->bcs[0].Flag, cs->bcs[1].Flag);
1302        printk(KERN_DEBUG "HiSax: bcs 0 mode %d ch%d\n",
1303               cs->bcs[0].mode, cs->bcs[0].channel);
1304        printk(KERN_DEBUG "HiSax: bcs 1 mode %d ch%d\n",
1305               cs->bcs[1].mode, cs->bcs[1].channel);
1306#ifdef ERROR_STATISTIC
1307        printk(KERN_DEBUG "HiSax: dc errors(rx,crc,tx) %d,%d,%d\n",
1308               cs->err_rx, cs->err_crc, cs->err_tx);
1309        printk(KERN_DEBUG
1310               "HiSax: bc0 errors(inv,rdo,crc,tx) %d,%d,%d,%d\n",
1311               cs->bcs[0].err_inv, cs->bcs[0].err_rdo, cs->bcs[0].err_crc,
1312               cs->bcs[0].err_tx);
1313        printk(KERN_DEBUG
1314               "HiSax: bc1 errors(inv,rdo,crc,tx) %d,%d,%d,%d\n",
1315               cs->bcs[1].err_inv, cs->bcs[1].err_rdo, cs->bcs[1].err_crc,
1316               cs->bcs[1].err_tx);
1317        if (sel == 99) {
1318                cs->err_rx  = 0;
1319                cs->err_crc = 0;
1320                cs->err_tx  = 0;
1321                cs->bcs[0].err_inv = 0;
1322                cs->bcs[0].err_rdo = 0;
1323                cs->bcs[0].err_crc = 0;
1324                cs->bcs[0].err_tx  = 0;
1325                cs->bcs[1].err_inv = 0;
1326                cs->bcs[1].err_rdo = 0;
1327                cs->bcs[1].err_crc = 0;
1328                cs->bcs[1].err_tx  = 0;
1329        }
1330#endif
1331}
1332
1333static int __init HiSax_init(void)
1334{
1335        int i, retval;
1336#ifdef MODULE
1337        int j;
1338        int nzproto = 0;
1339#endif
1340
1341        HiSaxVersion();
1342        retval = CallcNew();
1343        if (retval)
1344                goto out;
1345        retval = Isdnl3New();
1346        if (retval)
1347                goto out_callc;
1348        retval = Isdnl2New();
1349        if (retval)
1350                goto out_isdnl3;
1351        retval = TeiNew();
1352        if (retval)
1353                goto out_isdnl2;
1354        retval = Isdnl1New();
1355        if (retval)
1356                goto out_tei;
1357
1358#ifdef MODULE
1359        if (!type[0]) {
1360                /* We 'll register drivers later, but init basic functions */
1361                for (i = 0; i < HISAX_MAX_CARDS; i++)
1362                        cards[i].typ = 0;
1363                return 0;
1364        }
1365#ifdef CONFIG_HISAX_ELSA
1366        if (type[0] == ISDN_CTYPE_ELSA_PCMCIA) {
1367                /* we have exported  and return in this case */
1368                return 0;
1369        }
1370#endif
1371#ifdef CONFIG_HISAX_SEDLBAUER
1372        if (type[0] == ISDN_CTYPE_SEDLBAUER_PCMCIA) {
1373                /* we have to export  and return in this case */
1374                return 0;
1375        }
1376#endif
1377#ifdef CONFIG_HISAX_AVM_A1_PCMCIA
1378        if (type[0] == ISDN_CTYPE_A1_PCMCIA) {
1379                /* we have to export  and return in this case */
1380                return 0;
1381        }
1382#endif
1383#ifdef CONFIG_HISAX_HFC_SX
1384        if (type[0] == ISDN_CTYPE_HFC_SP_PCMCIA) {
1385                /* we have to export  and return in this case */
1386                return 0;
1387        }
1388#endif
1389#endif
1390        nrcards = 0;
1391#ifdef MODULE
1392        if (id)                 /* If id= string used */
1393                HiSax_id = id;
1394        for (i = j = 0; j < HISAX_MAX_CARDS; i++) {
1395                cards[j].typ = type[i];
1396                if (protocol[i]) {
1397                        cards[j].protocol = protocol[i];
1398                        nzproto++;
1399                } else {
1400                        cards[j].protocol = DEFAULT_PROTO;
1401                }
1402                switch (type[i]) {
1403                case ISDN_CTYPE_16_0:
1404                        cards[j].para[0] = irq[i];
1405                        cards[j].para[1] = mem[i];
1406                        cards[j].para[2] = io[i];
1407                        break;
1408
1409                case ISDN_CTYPE_8_0:
1410                        cards[j].para[0] = irq[i];
1411                        cards[j].para[1] = mem[i];
1412                        break;
1413
1414#ifdef IO0_IO1
1415                case ISDN_CTYPE_PNP:
1416                case ISDN_CTYPE_NICCY:
1417                        cards[j].para[0] = irq[i];
1418                        cards[j].para[1] = io0[i];
1419                        cards[j].para[2] = io1[i];
1420                        break;
1421                case ISDN_CTYPE_COMPAQ_ISA:
1422                        cards[j].para[0] = irq[i];
1423                        cards[j].para[1] = io0[i];
1424                        cards[j].para[2] = io1[i];
1425                        cards[j].para[3] = io[i];
1426                        break;
1427#endif
1428                case ISDN_CTYPE_ELSA:
1429                case ISDN_CTYPE_HFC_PCI:
1430                        cards[j].para[0] = io[i];
1431                        break;
1432                case ISDN_CTYPE_16_3:
1433                case ISDN_CTYPE_TELESPCMCIA:
1434                case ISDN_CTYPE_A1:
1435                case ISDN_CTYPE_A1_PCMCIA:
1436                case ISDN_CTYPE_ELSA_PNP:
1437                case ISDN_CTYPE_ELSA_PCMCIA:
1438                case ISDN_CTYPE_IX1MICROR2:
1439                case ISDN_CTYPE_DIEHLDIVA:
1440                case ISDN_CTYPE_ASUSCOM:
1441                case ISDN_CTYPE_TELEINT:
1442                case ISDN_CTYPE_SEDLBAUER:
1443                case ISDN_CTYPE_SEDLBAUER_PCMCIA:
1444                case ISDN_CTYPE_SEDLBAUER_FAX:
1445                case ISDN_CTYPE_SPORTSTER:
1446                case ISDN_CTYPE_MIC:
1447                case ISDN_CTYPE_TELES3C:
1448                case ISDN_CTYPE_ACERP10:
1449                case ISDN_CTYPE_S0BOX:
1450                case ISDN_CTYPE_FRITZPCI:
1451                case ISDN_CTYPE_HSTSAPHIR:
1452                case ISDN_CTYPE_GAZEL:
1453                case ISDN_CTYPE_HFC_SX:
1454                case ISDN_CTYPE_HFC_SP_PCMCIA:
1455                        cards[j].para[0] = irq[i];
1456                        cards[j].para[1] = io[i];
1457                        break;
1458                case ISDN_CTYPE_ISURF:
1459                        cards[j].para[0] = irq[i];
1460                        cards[j].para[1] = io[i];
1461                        cards[j].para[2] = mem[i];
1462                        break;
1463                case ISDN_CTYPE_ELSA_PCI:
1464                case ISDN_CTYPE_NETJET_S:
1465                case ISDN_CTYPE_TELESPCI:
1466                case ISDN_CTYPE_W6692:
1467                case ISDN_CTYPE_NETJET_U:
1468                        break;
1469                case ISDN_CTYPE_BKM_A4T:
1470                        break;
1471                case ISDN_CTYPE_SCT_QUADRO:
1472                        if (irq[i]) {
1473                                cards[j].para[0] = irq[i];
1474                        } else {
1475                                /* QUADRO is a 4 BRI card */
1476                                cards[j++].para[0] = 1;
1477                                /* we need to check if further cards can be added */
1478                                if (j < HISAX_MAX_CARDS) {
1479                                        cards[j].typ = ISDN_CTYPE_SCT_QUADRO;
1480                                        cards[j].protocol = protocol[i];
1481                                        cards[j++].para[0] = 2;
1482                                }
1483                                if (j < HISAX_MAX_CARDS) {
1484                                        cards[j].typ = ISDN_CTYPE_SCT_QUADRO;
1485                                        cards[j].protocol = protocol[i];
1486                                        cards[j++].para[0] = 3;
1487                                }
1488                                if (j < HISAX_MAX_CARDS) {
1489                                        cards[j].typ = ISDN_CTYPE_SCT_QUADRO;
1490                                        cards[j].protocol = protocol[i];
1491                                        cards[j].para[0] = 4;
1492                                }
1493                        }
1494                        break;
1495                }
1496                j++;
1497        }
1498        if (!nzproto) {
1499                printk(KERN_WARNING
1500                       "HiSax: Warning - no protocol specified\n");
1501                printk(KERN_WARNING "HiSax: using protocol %s\n",
1502                       DEFAULT_PROTO_NAME);
1503        }
1504#endif
1505        if (!HiSax_id)
1506                HiSax_id = HiSaxID;
1507        if (!HiSaxID[0])
1508                strcpy(HiSaxID, "HiSax");
1509        for (i = 0; i < HISAX_MAX_CARDS; i++)
1510                if (cards[i].typ > 0)
1511                        nrcards++;
1512        printk(KERN_DEBUG "HiSax: Total %d card%s defined\n",
1513               nrcards, (nrcards > 1) ? "s" : "");
1514
1515        /* Install only, if at least one card found */
1516        if (!HiSax_inithardware(NULL))
1517                return -ENODEV;
1518        return 0;
1519
1520out_tei:
1521        TeiFree();
1522out_isdnl2:
1523        Isdnl2Free();
1524out_isdnl3:
1525        Isdnl3Free();
1526out_callc:
1527        CallcFree();
1528out:
1529        return retval;
1530}
1531
1532static void __exit HiSax_exit(void)
1533{
1534        int cardnr = nrcards - 1;
1535
1536        while (cardnr >= 0)
1537                HiSax_closecard(cardnr--);
1538        Isdnl1Free();
1539        TeiFree();
1540        Isdnl2Free();
1541        Isdnl3Free();
1542        CallcFree();
1543        printk(KERN_INFO "HiSax module removed\n");
1544}
1545
1546int hisax_init_pcmcia(void *pcm_iob, int *busy_flag, struct IsdnCard *card)
1547{
1548        u_char ids[16];
1549        int ret = -1;
1550
1551        cards[nrcards] = *card;
1552        if (nrcards)
1553                sprintf(ids, "HiSax%d", nrcards);
1554        else
1555                sprintf(ids, "HiSax");
1556        if (!checkcard(nrcards, ids, busy_flag, THIS_MODULE,
1557                       hisax_cs_setup_card))
1558                goto error;
1559
1560        ret = nrcards;
1561        nrcards++;
1562error:
1563        return ret;
1564}
1565EXPORT_SYMBOL(hisax_init_pcmcia);
1566
1567EXPORT_SYMBOL(HiSax_closecard);
1568
1569#include "hisax_if.h"
1570
1571EXPORT_SYMBOL(hisax_register);
1572EXPORT_SYMBOL(hisax_unregister);
1573
1574static void hisax_d_l1l2(struct hisax_if *ifc, int pr, void *arg);
1575static void hisax_b_l1l2(struct hisax_if *ifc, int pr, void *arg);
1576static void hisax_d_l2l1(struct PStack *st, int pr, void *arg);
1577static void hisax_b_l2l1(struct PStack *st, int pr, void *arg);
1578static int hisax_cardmsg(struct IsdnCardState *cs, int mt, void *arg);
1579static int hisax_bc_setstack(struct PStack *st, struct BCState *bcs);
1580static void hisax_bc_close(struct BCState *bcs);
1581static void hisax_bh(struct work_struct *work);
1582static void EChannel_proc_rcv(struct hisax_d_if *d_if);
1583
1584static int hisax_setup_card_dynamic(struct IsdnCard *card)
1585{
1586        return 2;
1587}
1588
1589int hisax_register(struct hisax_d_if *hisax_d_if, struct hisax_b_if *b_if[],
1590                   char *name, int protocol)
1591{
1592        int i, retval;
1593        char id[20];
1594        struct IsdnCardState *cs;
1595
1596        for (i = 0; i < HISAX_MAX_CARDS; i++) {
1597                if (!cards[i].typ)
1598                        break;
1599        }
1600
1601        if (i >= HISAX_MAX_CARDS)
1602                return -EBUSY;
1603
1604        cards[i].typ = ISDN_CTYPE_DYNAMIC;
1605        cards[i].protocol = protocol;
1606        sprintf(id, "%s%d", name, i);
1607        nrcards++;
1608        retval = checkcard(i, id, NULL, hisax_d_if->owner,
1609                           hisax_setup_card_dynamic);
1610        if (retval == 0) { // yuck
1611                cards[i].typ = 0;
1612                nrcards--;
1613                return -EINVAL;
1614        }
1615        cs = cards[i].cs;
1616        hisax_d_if->cs = cs;
1617        cs->hw.hisax_d_if = hisax_d_if;
1618        cs->cardmsg = hisax_cardmsg;
1619        INIT_WORK(&cs->tqueue, hisax_bh);
1620        cs->channel[0].d_st->l2.l2l1 = hisax_d_l2l1;
1621        for (i = 0; i < 2; i++) {
1622                cs->bcs[i].BC_SetStack = hisax_bc_setstack;
1623                cs->bcs[i].BC_Close = hisax_bc_close;
1624
1625                b_if[i]->ifc.l1l2 = hisax_b_l1l2;
1626
1627                hisax_d_if->b_if[i] = b_if[i];
1628        }
1629        hisax_d_if->ifc.l1l2 = hisax_d_l1l2;
1630        skb_queue_head_init(&hisax_d_if->erq);
1631        clear_bit(0, &hisax_d_if->ph_state);
1632
1633        return 0;
1634}
1635
1636void hisax_unregister(struct hisax_d_if *hisax_d_if)
1637{
1638        cards[hisax_d_if->cs->cardnr].typ = 0;
1639        HiSax_closecard(hisax_d_if->cs->cardnr);
1640        skb_queue_purge(&hisax_d_if->erq);
1641}
1642
1643#include "isdnl1.h"
1644
1645static void hisax_sched_event(struct IsdnCardState *cs, int event)
1646{
1647        test_and_set_bit(event, &cs->event);
1648        schedule_work(&cs->tqueue);
1649}
1650
1651static void hisax_bh(struct work_struct *work)
1652{
1653        struct IsdnCardState *cs =
1654                container_of(work, struct IsdnCardState, tqueue);
1655        struct PStack *st;
1656        int pr;
1657
1658        if (test_and_clear_bit(D_RCVBUFREADY, &cs->event))
1659                DChannel_proc_rcv(cs);
1660        if (test_and_clear_bit(E_RCVBUFREADY, &cs->event))
1661                EChannel_proc_rcv(cs->hw.hisax_d_if);
1662        if (test_and_clear_bit(D_L1STATECHANGE, &cs->event)) {
1663                if (test_bit(0, &cs->hw.hisax_d_if->ph_state))
1664                        pr = PH_ACTIVATE | INDICATION;
1665                else
1666                        pr = PH_DEACTIVATE | INDICATION;
1667                for (st = cs->stlist; st; st = st->next)
1668                        st->l1.l1l2(st, pr, NULL);
1669
1670        }
1671}
1672
1673static void hisax_b_sched_event(struct BCState *bcs, int event)
1674{
1675        test_and_set_bit(event, &bcs->event);
1676        schedule_work(&bcs->tqueue);
1677}
1678
1679static inline void D_L2L1(struct hisax_d_if *d_if, int pr, void *arg)
1680{
1681        struct hisax_if *ifc = (struct hisax_if *) d_if;
1682        ifc->l2l1(ifc, pr, arg);
1683}
1684
1685static inline void B_L2L1(struct hisax_b_if *b_if, int pr, void *arg)
1686{
1687        struct hisax_if *ifc = (struct hisax_if *) b_if;
1688        ifc->l2l1(ifc, pr, arg);
1689}
1690
1691static void hisax_d_l1l2(struct hisax_if *ifc, int pr, void *arg)
1692{
1693        struct hisax_d_if *d_if = (struct hisax_d_if *) ifc;
1694        struct IsdnCardState *cs = d_if->cs;
1695        struct PStack *st;
1696        struct sk_buff *skb;
1697
1698        switch (pr) {
1699        case PH_ACTIVATE | INDICATION:
1700                set_bit(0, &d_if->ph_state);
1701                hisax_sched_event(cs, D_L1STATECHANGE);
1702                break;
1703        case PH_DEACTIVATE | INDICATION:
1704                clear_bit(0, &d_if->ph_state);
1705                hisax_sched_event(cs, D_L1STATECHANGE);
1706                break;
1707        case PH_DATA | INDICATION:
1708                skb_queue_tail(&cs->rq, arg);
1709                hisax_sched_event(cs, D_RCVBUFREADY);
1710                break;
1711        case PH_DATA | CONFIRM:
1712                skb = skb_dequeue(&cs->sq);
1713                if (skb) {
1714                        D_L2L1(d_if, PH_DATA | REQUEST, skb);
1715                        break;
1716                }
1717                clear_bit(FLG_L1_DBUSY, &cs->HW_Flags);
1718                for (st = cs->stlist; st; st = st->next) {
1719                        if (test_and_clear_bit(FLG_L1_PULL_REQ, &st->l1.Flags)) {
1720                                st->l1.l1l2(st, PH_PULL | CONFIRM, NULL);
1721                                break;
1722                        }
1723                }
1724                break;
1725        case PH_DATA_E | INDICATION:
1726                skb_queue_tail(&d_if->erq, arg);
1727                hisax_sched_event(cs, E_RCVBUFREADY);
1728                break;
1729        default:
1730                printk("pr %#x\n", pr);
1731                break;
1732        }
1733}
1734
1735static void hisax_b_l1l2(struct hisax_if *ifc, int pr, void *arg)
1736{
1737        struct hisax_b_if *b_if = (struct hisax_b_if *) ifc;
1738        struct BCState *bcs = b_if->bcs;
1739        struct PStack *st = bcs->st;
1740        struct sk_buff *skb;
1741
1742        // FIXME use isdnl1?
1743        switch (pr) {
1744        case PH_ACTIVATE | INDICATION:
1745                st->l1.l1l2(st, pr, NULL);
1746                break;
1747        case PH_DEACTIVATE | INDICATION:
1748                st->l1.l1l2(st, pr, NULL);
1749                clear_bit(BC_FLG_BUSY, &bcs->Flag);
1750                skb_queue_purge(&bcs->squeue);
1751                bcs->hw.b_if = NULL;
1752                break;
1753        case PH_DATA | INDICATION:
1754                skb_queue_tail(&bcs->rqueue, arg);
1755                hisax_b_sched_event(bcs, B_RCVBUFREADY);
1756                break;
1757        case PH_DATA | CONFIRM:
1758                bcs->tx_cnt -= (long)arg;
1759                if (test_bit(FLG_LLI_L1WAKEUP, &bcs->st->lli.flag)) {
1760                        u_long  flags;
1761                        spin_lock_irqsave(&bcs->aclock, flags);
1762                        bcs->ackcnt += (long)arg;
1763                        spin_unlock_irqrestore(&bcs->aclock, flags);
1764                        schedule_event(bcs, B_ACKPENDING);
1765                }
1766                skb = skb_dequeue(&bcs->squeue);
1767                if (skb) {
1768                        B_L2L1(b_if, PH_DATA | REQUEST, skb);
1769                        break;
1770                }
1771                clear_bit(BC_FLG_BUSY, &bcs->Flag);
1772                if (test_and_clear_bit(FLG_L1_PULL_REQ, &st->l1.Flags)) {
1773                        st->l1.l1l2(st, PH_PULL | CONFIRM, NULL);
1774                }
1775                break;
1776        default:
1777                printk("hisax_b_l1l2 pr %#x\n", pr);
1778                break;
1779        }
1780}
1781
1782static void hisax_d_l2l1(struct PStack *st, int pr, void *arg)
1783{
1784        struct IsdnCardState *cs = st->l1.hardware;
1785        struct hisax_d_if *hisax_d_if = cs->hw.hisax_d_if;
1786        struct sk_buff *skb = arg;
1787
1788        switch (pr) {
1789        case PH_DATA | REQUEST:
1790        case PH_PULL | INDICATION:
1791                if (cs->debug & DEB_DLOG_HEX)
1792                        LogFrame(cs, skb->data, skb->len);
1793                if (cs->debug & DEB_DLOG_VERBOSE)
1794                        dlogframe(cs, skb, 0);
1795                Logl2Frame(cs, skb, "PH_DATA_REQ", 0);
1796                // FIXME lock?
1797                if (!test_and_set_bit(FLG_L1_DBUSY, &cs->HW_Flags))
1798                        D_L2L1(hisax_d_if, PH_DATA | REQUEST, skb);
1799                else
1800                        skb_queue_tail(&cs->sq, skb);
1801                break;
1802        case PH_PULL | REQUEST:
1803                if (!test_bit(FLG_L1_DBUSY, &cs->HW_Flags))
1804                        st->l1.l1l2(st, PH_PULL | CONFIRM, NULL);
1805                else
1806                        set_bit(FLG_L1_PULL_REQ, &st->l1.Flags);
1807                break;
1808        default:
1809                D_L2L1(hisax_d_if, pr, arg);
1810                break;
1811        }
1812}
1813
1814static int hisax_cardmsg(struct IsdnCardState *cs, int mt, void *arg)
1815{
1816        return 0;
1817}
1818
1819static void hisax_b_l2l1(struct PStack *st, int pr, void *arg)
1820{
1821        struct BCState *bcs = st->l1.bcs;
1822        struct hisax_b_if *b_if = bcs->hw.b_if;
1823
1824        switch (pr) {
1825        case PH_ACTIVATE | REQUEST:
1826                B_L2L1(b_if, pr, (void *)(unsigned long)st->l1.mode);
1827                break;
1828        case PH_DATA | REQUEST:
1829        case PH_PULL | INDICATION:
1830                // FIXME lock?
1831                if (!test_and_set_bit(BC_FLG_BUSY, &bcs->Flag)) {
1832                        B_L2L1(b_if, PH_DATA | REQUEST, arg);
1833                } else {
1834                        skb_queue_tail(&bcs->squeue, arg);
1835                }
1836                break;
1837        case PH_PULL | REQUEST:
1838                if (!test_bit(BC_FLG_BUSY, &bcs->Flag))
1839                        st->l1.l1l2(st, PH_PULL | CONFIRM, NULL);
1840                else
1841                        set_bit(FLG_L1_PULL_REQ, &st->l1.Flags);
1842                break;
1843        case PH_DEACTIVATE | REQUEST:
1844                test_and_clear_bit(BC_FLG_BUSY, &bcs->Flag);
1845                skb_queue_purge(&bcs->squeue);
1846        default:
1847                B_L2L1(b_if, pr, arg);
1848                break;
1849        }
1850}
1851
1852static int hisax_bc_setstack(struct PStack *st, struct BCState *bcs)
1853{
1854        struct IsdnCardState *cs = st->l1.hardware;
1855        struct hisax_d_if *hisax_d_if = cs->hw.hisax_d_if;
1856
1857        bcs->channel = st->l1.bc;
1858
1859        bcs->hw.b_if = hisax_d_if->b_if[st->l1.bc];
1860        hisax_d_if->b_if[st->l1.bc]->bcs = bcs;
1861
1862        st->l1.bcs = bcs;
1863        st->l2.l2l1 = hisax_b_l2l1;
1864        setstack_manager(st);
1865        bcs->st = st;
1866        setstack_l1_B(st);
1867        skb_queue_head_init(&bcs->rqueue);
1868        skb_queue_head_init(&bcs->squeue);
1869        return 0;
1870}
1871
1872static void hisax_bc_close(struct BCState *bcs)
1873{
1874        struct hisax_b_if *b_if = bcs->hw.b_if;
1875
1876        if (b_if)
1877                B_L2L1(b_if, PH_DEACTIVATE | REQUEST, NULL);
1878}
1879
1880static void EChannel_proc_rcv(struct hisax_d_if *d_if)
1881{
1882        struct IsdnCardState *cs = d_if->cs;
1883        u_char *ptr;
1884        struct sk_buff *skb;
1885
1886        while ((skb = skb_dequeue(&d_if->erq)) != NULL) {
1887                if (cs->debug & DEB_DLOG_HEX) {
1888                        ptr = cs->dlog;
1889                        if ((skb->len) < MAX_DLOG_SPACE / 3 - 10) {
1890                                *ptr++ = 'E';
1891                                *ptr++ = 'C';
1892                                *ptr++ = 'H';
1893                                *ptr++ = 'O';
1894                                *ptr++ = ':';
1895                                ptr += QuickHex(ptr, skb->data, skb->len);
1896                                ptr--;
1897                                *ptr++ = '\n';
1898                                *ptr = 0;
1899                                HiSax_putstatus(cs, NULL, cs->dlog);
1900                        } else
1901                                HiSax_putstatus(cs, "LogEcho: ",
1902                                                "warning Frame too big (%d)",
1903                                                skb->len);
1904                }
1905                dev_kfree_skb_any(skb);
1906        }
1907}
1908
1909#ifdef CONFIG_PCI
1910#include <linux/pci.h>
1911
1912static const struct pci_device_id hisax_pci_tbl[] __used = {
1913#ifdef CONFIG_HISAX_FRITZPCI
1914        {PCI_VDEVICE(AVM,      PCI_DEVICE_ID_AVM_A1)                    },
1915#endif
1916#ifdef CONFIG_HISAX_DIEHLDIVA
1917        {PCI_VDEVICE(EICON,    PCI_DEVICE_ID_EICON_DIVA20)              },
1918        {PCI_VDEVICE(EICON,    PCI_DEVICE_ID_EICON_DIVA20_U)    },
1919        {PCI_VDEVICE(EICON,    PCI_DEVICE_ID_EICON_DIVA201)             },
1920/*##########################################################################*/
1921        {PCI_VDEVICE(EICON,    PCI_DEVICE_ID_EICON_DIVA202)             },
1922/*##########################################################################*/
1923#endif
1924#ifdef CONFIG_HISAX_ELSA
1925        {PCI_VDEVICE(ELSA,     PCI_DEVICE_ID_ELSA_MICROLINK)    },
1926        {PCI_VDEVICE(ELSA,     PCI_DEVICE_ID_ELSA_QS3000)               },
1927#endif
1928#ifdef CONFIG_HISAX_GAZEL
1929        {PCI_VDEVICE(PLX,      PCI_DEVICE_ID_PLX_R685)                  },
1930        {PCI_VDEVICE(PLX,      PCI_DEVICE_ID_PLX_R753)                  },
1931        {PCI_VDEVICE(PLX,      PCI_DEVICE_ID_PLX_DJINN_ITOO)    },
1932        {PCI_VDEVICE(PLX,      PCI_DEVICE_ID_PLX_OLITEC)                },
1933#endif
1934#ifdef CONFIG_HISAX_SCT_QUADRO
1935        {PCI_VDEVICE(PLX,      PCI_DEVICE_ID_PLX_9050)                  },
1936#endif
1937#ifdef CONFIG_HISAX_NICCY
1938        {PCI_VDEVICE(SATSAGEM, PCI_DEVICE_ID_SATSAGEM_NICCY)    },
1939#endif
1940#ifdef CONFIG_HISAX_SEDLBAUER
1941        {PCI_VDEVICE(TIGERJET, PCI_DEVICE_ID_TIGERJET_100)              },
1942#endif
1943#if defined(CONFIG_HISAX_NETJET) || defined(CONFIG_HISAX_NETJET_U)
1944        {PCI_VDEVICE(TIGERJET, PCI_DEVICE_ID_TIGERJET_300)              },
1945#endif
1946#if defined(CONFIG_HISAX_TELESPCI) || defined(CONFIG_HISAX_SCT_QUADRO)
1947        {PCI_VDEVICE(ZORAN,    PCI_DEVICE_ID_ZORAN_36120)               },
1948#endif
1949#ifdef CONFIG_HISAX_W6692
1950        {PCI_VDEVICE(DYNALINK, PCI_DEVICE_ID_DYNALINK_IS64PH)   },
1951        {PCI_VDEVICE(WINBOND2, PCI_DEVICE_ID_WINBOND2_6692)             },
1952#endif
1953#ifdef CONFIG_HISAX_HFC_PCI
1954        {PCI_VDEVICE(CCD,      PCI_DEVICE_ID_CCD_2BD0)                  },
1955        {PCI_VDEVICE(CCD,      PCI_DEVICE_ID_CCD_B000)                  },
1956        {PCI_VDEVICE(CCD,      PCI_DEVICE_ID_CCD_B006)                  },
1957        {PCI_VDEVICE(CCD,      PCI_DEVICE_ID_CCD_B007)                  },
1958        {PCI_VDEVICE(CCD,      PCI_DEVICE_ID_CCD_B008)                  },
1959        {PCI_VDEVICE(CCD,      PCI_DEVICE_ID_CCD_B009)                  },
1960        {PCI_VDEVICE(CCD,      PCI_DEVICE_ID_CCD_B00A)                  },
1961        {PCI_VDEVICE(CCD,      PCI_DEVICE_ID_CCD_B00B)                  },
1962        {PCI_VDEVICE(CCD,      PCI_DEVICE_ID_CCD_B00C)                  },
1963        {PCI_VDEVICE(CCD,      PCI_DEVICE_ID_CCD_B100)                  },
1964        {PCI_VDEVICE(CCD,      PCI_DEVICE_ID_CCD_B700)                  },
1965        {PCI_VDEVICE(CCD,      PCI_DEVICE_ID_CCD_B701)                  },
1966        {PCI_VDEVICE(ABOCOM,   PCI_DEVICE_ID_ABOCOM_2BD1)               },
1967        {PCI_VDEVICE(ASUSTEK,  PCI_DEVICE_ID_ASUSTEK_0675)              },
1968        {PCI_VDEVICE(BERKOM,   PCI_DEVICE_ID_BERKOM_T_CONCEPT)  },
1969        {PCI_VDEVICE(BERKOM,   PCI_DEVICE_ID_BERKOM_A1T)                },
1970        {PCI_VDEVICE(ANIGMA,   PCI_DEVICE_ID_ANIGMA_MC145575)   },
1971        {PCI_VDEVICE(ZOLTRIX,  PCI_DEVICE_ID_ZOLTRIX_2BD0)              },
1972        {PCI_VDEVICE(DIGI,     PCI_DEVICE_ID_DIGI_DF_M_IOM2_E)  },
1973        {PCI_VDEVICE(DIGI,     PCI_DEVICE_ID_DIGI_DF_M_E)               },
1974        {PCI_VDEVICE(DIGI,     PCI_DEVICE_ID_DIGI_DF_M_IOM2_A)  },
1975        {PCI_VDEVICE(DIGI,     PCI_DEVICE_ID_DIGI_DF_M_A)               },
1976#endif
1977        { }                             /* Terminating entry */
1978};
1979
1980MODULE_DEVICE_TABLE(pci, hisax_pci_tbl);
1981#endif /* CONFIG_PCI */
1982
1983module_init(HiSax_init);
1984module_exit(HiSax_exit);
1985
1986EXPORT_SYMBOL(FsmNew);
1987EXPORT_SYMBOL(FsmFree);
1988EXPORT_SYMBOL(FsmEvent);
1989EXPORT_SYMBOL(FsmChangeState);
1990EXPORT_SYMBOL(FsmInitTimer);
1991EXPORT_SYMBOL(FsmDelTimer);
1992EXPORT_SYMBOL(FsmRestartTimer);
1993