Loading drivers/isdn/hardware/avm/avm_cs.c +23 −57 Original line number Diff line number Diff line Loading @@ -154,45 +154,33 @@ static void avmcs_detach(struct pcmcia_device *link) ======================================================================*/ static int get_tuple(struct pcmcia_device *handle, tuple_t *tuple, cisparse_t *parse) static int avmcs_configcheck(struct pcmcia_device *p_dev, cistpl_cftable_entry_t *cf, void *priv_data) { int i = pcmcia_get_tuple_data(handle, tuple); if (i != CS_SUCCESS) return i; return pcmcia_parse_tuple(handle, tuple, parse); } static int first_tuple(struct pcmcia_device *handle, tuple_t *tuple, cisparse_t *parse) { int i = pcmcia_get_first_tuple(handle, tuple); if (i != CS_SUCCESS) return i; return get_tuple(handle, tuple, parse); } if (cf->io.nwin <= 0) return -ENODEV; static int next_tuple(struct pcmcia_device *handle, tuple_t *tuple, cisparse_t *parse) { int i = pcmcia_get_next_tuple(handle, tuple); if (i != CS_SUCCESS) return i; return get_tuple(handle, tuple, parse); p_dev->conf.ConfigIndex = cf->index; p_dev->io.BasePort1 = cf->io.win[0].base; p_dev->io.NumPorts1 = cf->io.win[0].len; p_dev->io.NumPorts2 = 0; printk(KERN_INFO "avm_cs: testing i/o %#x-%#x\n", p_dev->io.BasePort1, p_dev->io.BasePort1+p_dev->io.NumPorts1-1); return pcmcia_request_io(p_dev, &p_dev->io); } static int avmcs_config(struct pcmcia_device *link) { tuple_t tuple; cisparse_t parse; cistpl_cftable_entry_t *cf = &parse.cftable_entry; local_info_t *dev; int i; u_char buf[64]; char devname[128]; int cardtype; int (*addcard)(unsigned int port, unsigned irq); dev = link->priv; do { devname[0] = 0; if (link->prod_id[1]) strlcpy(devname, link->prod_id[1], sizeof(devname)); Loading @@ -200,32 +188,10 @@ static int avmcs_config(struct pcmcia_device *link) /* * find IO port */ tuple.TupleData = (cisdata_t *)buf; tuple.TupleOffset = 0; tuple.TupleDataMax = 255; tuple.Attributes = 0; tuple.DesiredTuple = CISTPL_CFTABLE_ENTRY; i = first_tuple(link, &tuple, &parse); while (i == CS_SUCCESS) { if (cf->io.nwin > 0) { link->conf.ConfigIndex = cf->index; link->io.BasePort1 = cf->io.win[0].base; link->io.NumPorts1 = cf->io.win[0].len; link->io.NumPorts2 = 0; printk(KERN_INFO "avm_cs: testing i/o %#x-%#x\n", link->io.BasePort1, link->io.BasePort1+link->io.NumPorts1-1); i = pcmcia_request_io(link, &link->io); if (i == CS_SUCCESS) goto found_port; } i = next_tuple(link, &tuple, &parse); } found_port: if (i != CS_SUCCESS) { cs_error(link, RequestIO, i); break; } if (pcmcia_loop_config(link, avmcs_configcheck, NULL)) return -ENODEV; do { /* * allocate an interrupt line */ Loading drivers/isdn/hisax/avma1_cs.c +20 −56 Original line number Diff line number Diff line Loading @@ -174,38 +174,28 @@ static void avma1cs_detach(struct pcmcia_device *link) ======================================================================*/ static int get_tuple(struct pcmcia_device *handle, tuple_t *tuple, cisparse_t *parse) static int avma1cs_configcheck(struct pcmcia_device *p_dev, cistpl_cftable_entry_t *cf, void *priv_data) { int i = pcmcia_get_tuple_data(handle, tuple); if (i != CS_SUCCESS) return i; return pcmcia_parse_tuple(handle, tuple, parse); } if (cf->io.nwin <= 0) return -ENODEV; static int first_tuple(struct pcmcia_device *handle, tuple_t *tuple, cisparse_t *parse) { int i = pcmcia_get_first_tuple(handle, tuple); if (i != CS_SUCCESS) return i; return get_tuple(handle, tuple, parse); p_dev->conf.ConfigIndex = cf->index; p_dev->io.BasePort1 = cf->io.win[0].base; p_dev->io.NumPorts1 = cf->io.win[0].len; p_dev->io.NumPorts2 = 0; printk(KERN_INFO "avma1_cs: testing i/o %#x-%#x\n", p_dev->io.BasePort1, p_dev->io.BasePort1+p_dev->io.NumPorts1-1); return pcmcia_request_io(p_dev, &p_dev->io); } static int next_tuple(struct pcmcia_device *handle, tuple_t *tuple, cisparse_t *parse) { int i = pcmcia_get_next_tuple(handle, tuple); if (i != CS_SUCCESS) return i; return get_tuple(handle, tuple, parse); } static int avma1cs_config(struct pcmcia_device *link) { tuple_t tuple; cisparse_t parse; cistpl_cftable_entry_t *cf = &parse.cftable_entry; local_info_t *dev; int i; u_char buf[64]; char devname[128]; IsdnCard_t icard; int busy = 0; Loading @@ -214,40 +204,14 @@ static int avma1cs_config(struct pcmcia_device *link) DEBUG(0, "avma1cs_config(0x%p)\n", link); do { devname[0] = 0; if (link->prod_id[1]) strlcpy(devname, link->prod_id[1], sizeof(devname)); /* * find IO port */ tuple.TupleData = (cisdata_t *)buf; tuple.TupleOffset = 0; tuple.TupleDataMax = 255; tuple.Attributes = 0; tuple.DesiredTuple = CISTPL_CFTABLE_ENTRY; i = first_tuple(link, &tuple, &parse); while (i == CS_SUCCESS) { if (cf->io.nwin > 0) { link->conf.ConfigIndex = cf->index; link->io.BasePort1 = cf->io.win[0].base; link->io.NumPorts1 = cf->io.win[0].len; link->io.NumPorts2 = 0; printk(KERN_INFO "avma1_cs: testing i/o %#x-%#x\n", link->io.BasePort1, link->io.BasePort1+link->io.NumPorts1 - 1); i = pcmcia_request_io(link, &link->io); if (i == CS_SUCCESS) goto found_port; } i = next_tuple(link, &tuple, &parse); } found_port: if (i != CS_SUCCESS) { cs_error(link, RequestIO, i); break; } if (pcmcia_loop_config(link, avma1cs_configcheck, NULL)) return -ENODEV; do { /* * allocate an interrupt line */ Loading drivers/isdn/hisax/elsa_cs.c +23 −50 Original line number Diff line number Diff line Loading @@ -203,68 +203,41 @@ static void elsa_cs_detach(struct pcmcia_device *link) device available to the system. ======================================================================*/ static int get_tuple(struct pcmcia_device *handle, tuple_t *tuple, cisparse_t *parse) { int i = pcmcia_get_tuple_data(handle, tuple); if (i != CS_SUCCESS) return i; return pcmcia_parse_tuple(handle, tuple, parse); } static int first_tuple(struct pcmcia_device *handle, tuple_t *tuple, cisparse_t *parse) static int elsa_cs_configcheck(struct pcmcia_device *p_dev, cistpl_cftable_entry_t *cf, void *priv_data) { int i = pcmcia_get_first_tuple(handle, tuple); if (i != CS_SUCCESS) return i; return get_tuple(handle, tuple, parse); } int j; static int next_tuple(struct pcmcia_device *handle, tuple_t *tuple, cisparse_t *parse) { int i = pcmcia_get_next_tuple(handle, tuple); if (i != CS_SUCCESS) return i; return get_tuple(handle, tuple, parse); if ((cf->io.nwin > 0) && cf->io.win[0].base) { printk(KERN_INFO "(elsa_cs: looks like the 96 model)\n"); p_dev->conf.ConfigIndex = cf->index; p_dev->io.BasePort1 = cf->io.win[0].base; if (!pcmcia_request_io(p_dev, &p_dev->io)) return 0; } else { printk(KERN_INFO "(elsa_cs: looks like the 97 model)\n"); p_dev->conf.ConfigIndex = cf->index; for (j = 0x2f0; j > 0x100; j -= 0x10) { p_dev->io.BasePort1 = j; if (!pcmcia_request_io(p_dev, &p_dev->io)) return 0; } } return -ENODEV; } static int elsa_cs_config(struct pcmcia_device *link) { tuple_t tuple; cisparse_t parse; local_info_t *dev; int i, j, last_fn; u_short buf[128]; cistpl_cftable_entry_t *cf = &parse.cftable_entry; int i, last_fn; IsdnCard_t icard; DEBUG(0, "elsa_config(0x%p)\n", link); dev = link->priv; tuple.TupleData = (cisdata_t *)buf; tuple.TupleOffset = 0; tuple.TupleDataMax = 255; tuple.Attributes = 0; tuple.DesiredTuple = CISTPL_CFTABLE_ENTRY; i = first_tuple(link, &tuple, &parse); while (i == CS_SUCCESS) { if ( (cf->io.nwin > 0) && cf->io.win[0].base) { printk(KERN_INFO "(elsa_cs: looks like the 96 model)\n"); link->conf.ConfigIndex = cf->index; link->io.BasePort1 = cf->io.win[0].base; i = pcmcia_request_io(link, &link->io); if (i == CS_SUCCESS) break; } else { printk(KERN_INFO "(elsa_cs: looks like the 97 model)\n"); link->conf.ConfigIndex = cf->index; for (i = 0, j = 0x2f0; j > 0x100; j -= 0x10) { link->io.BasePort1 = j; i = pcmcia_request_io(link, &link->io); if (i == CS_SUCCESS) break; } break; } i = next_tuple(link, &tuple, &parse); } i = pcmcia_loop_config(link, elsa_cs_configcheck, NULL); if (i != CS_SUCCESS) { last_fn = RequestIO; goto cs_failed; Loading drivers/isdn/hisax/sedlbauer_cs.c +102 −106 Original line number Diff line number Diff line Loading @@ -217,101 +217,68 @@ static void sedlbauer_detach(struct pcmcia_device *link) #define CS_CHECK(fn, ret) \ do { last_fn = (fn); if ((last_ret = (ret)) != 0) goto cs_failed; } while (0) static int sedlbauer_config(struct pcmcia_device *link) { local_info_t *dev = link->priv; tuple_t tuple; cisparse_t parse; int last_fn, last_ret; u8 buf[64]; struct sedlbauer_config_data { cistpl_cftable_entry_t dflt; config_info_t conf; win_req_t req; memreq_t map; IsdnCard_t icard; DEBUG(0, "sedlbauer_config(0x%p)\n", link); tuple.Attributes = 0; tuple.TupleData = buf; tuple.TupleDataMax = sizeof(buf); tuple.TupleOffset = 0; CS_CHECK(GetConfigurationInfo, pcmcia_get_configuration_info(link, &conf)); }; /* In this loop, we scan the CIS for configuration table entries, each of which describes a valid card configuration, including voltage, IO window, memory window, and interrupt settings. static int sedlbauer_config_check(struct pcmcia_device *p_dev, cistpl_cftable_entry_t *cfg, void *priv_data) { struct sedlbauer_config_data *cfg_mem = priv_data; We make no assumptions about the card to be configured: we use just the information available in the CIS. In an ideal world, this would work for any PCMCIA card, but it requires a complete and accurate CIS. In practice, a driver usually "knows" most of these things without consulting the CIS, and most client drivers will only use the CIS to fill in implementation-defined details. */ tuple.DesiredTuple = CISTPL_CFTABLE_ENTRY; CS_CHECK(GetFirstTuple, pcmcia_get_first_tuple(link, &tuple)); while (1) { cistpl_cftable_entry_t dflt = { 0 }; cistpl_cftable_entry_t *cfg = &(parse.cftable_entry); if (pcmcia_get_tuple_data(link, &tuple) != 0 || pcmcia_parse_tuple(link, &tuple, &parse) != 0) goto next_entry; if (cfg->flags & CISTPL_CFTABLE_DEFAULT) dflt = *cfg; if (cfg->index == 0) goto next_entry; link->conf.ConfigIndex = cfg->index; if (cfg->flags & CISTPL_CFTABLE_DEFAULT) cfg_mem->dflt = *cfg; if (cfg->index == 0) return -ENODEV; p_dev->conf.ConfigIndex = cfg->index; /* Does this card need audio output? */ if (cfg->flags & CISTPL_CFTABLE_AUDIO) { link->conf.Attributes |= CONF_ENABLE_SPKR; link->conf.Status = CCSR_AUDIO_ENA; p_dev->conf.Attributes |= CONF_ENABLE_SPKR; p_dev->conf.Status = CCSR_AUDIO_ENA; } /* Use power settings for Vcc and Vpp if present */ /* Note that the CIS values need to be rescaled */ if (cfg->vcc.present & (1<<CISTPL_POWER_VNOM)) { if (conf.Vcc != cfg->vcc.param[CISTPL_POWER_VNOM]/10000) goto next_entry; } else if (dflt.vcc.present & (1<<CISTPL_POWER_VNOM)) { if (conf.Vcc != dflt.vcc.param[CISTPL_POWER_VNOM]/10000) goto next_entry; if (cfg_mem->conf.Vcc != cfg->vcc.param[CISTPL_POWER_VNOM]/10000) return -ENODEV; } else if (cfg_mem->dflt.vcc.present & (1<<CISTPL_POWER_VNOM)) { if (cfg_mem->conf.Vcc != cfg_mem->dflt.vcc.param[CISTPL_POWER_VNOM]/10000) return -ENODEV; } if (cfg->vpp1.present & (1<<CISTPL_POWER_VNOM)) link->conf.Vpp = cfg->vpp1.param[CISTPL_POWER_VNOM]/10000; else if (dflt.vpp1.present & (1<<CISTPL_POWER_VNOM)) link->conf.Vpp = dflt.vpp1.param[CISTPL_POWER_VNOM]/10000; p_dev->conf.Vpp = cfg->vpp1.param[CISTPL_POWER_VNOM]/10000; else if (cfg_mem->dflt.vpp1.present & (1<<CISTPL_POWER_VNOM)) p_dev->conf.Vpp = cfg_mem->dflt.vpp1.param[CISTPL_POWER_VNOM]/10000; /* Do we need to allocate an interrupt? */ if (cfg->irq.IRQInfo1 || dflt.irq.IRQInfo1) link->conf.Attributes |= CONF_ENABLE_IRQ; if (cfg->irq.IRQInfo1 || cfg_mem->dflt.irq.IRQInfo1) p_dev->conf.Attributes |= CONF_ENABLE_IRQ; /* IO window settings */ link->io.NumPorts1 = link->io.NumPorts2 = 0; if ((cfg->io.nwin > 0) || (dflt.io.nwin > 0)) { cistpl_io_t *io = (cfg->io.nwin) ? &cfg->io : &dflt.io; link->io.Attributes1 = IO_DATA_PATH_WIDTH_AUTO; p_dev->io.NumPorts1 = p_dev->io.NumPorts2 = 0; if ((cfg->io.nwin > 0) || (cfg_mem->dflt.io.nwin > 0)) { cistpl_io_t *io = (cfg->io.nwin) ? &cfg->io : &cfg_mem->dflt.io; p_dev->io.Attributes1 = IO_DATA_PATH_WIDTH_AUTO; if (!(io->flags & CISTPL_IO_8BIT)) link->io.Attributes1 = IO_DATA_PATH_WIDTH_16; p_dev->io.Attributes1 = IO_DATA_PATH_WIDTH_16; if (!(io->flags & CISTPL_IO_16BIT)) link->io.Attributes1 = IO_DATA_PATH_WIDTH_8; /* new in dummy.cs 2001/01/28 MN link->io.IOAddrLines = io->flags & CISTPL_IO_LINES_MASK; */ link->io.BasePort1 = io->win[0].base; link->io.NumPorts1 = io->win[0].len; p_dev->io.Attributes1 = IO_DATA_PATH_WIDTH_8; p_dev->io.BasePort1 = io->win[0].base; p_dev->io.NumPorts1 = io->win[0].len; if (io->nwin > 1) { link->io.Attributes2 = link->io.Attributes1; link->io.BasePort2 = io->win[1].base; link->io.NumPorts2 = io->win[1].len; p_dev->io.Attributes2 = p_dev->io.Attributes1; p_dev->io.BasePort2 = io->win[1].base; p_dev->io.NumPorts2 = io->win[1].len; } /* This reserves IO space but doesn't actually enable it */ if (pcmcia_request_io(link, &link->io) != 0) goto next_entry; if (pcmcia_request_io(p_dev, &p_dev->io) != 0) return -ENODEV; } /* Loading @@ -325,31 +292,59 @@ static int sedlbauer_config(struct pcmcia_device *link) needs to be mapped to virtual space with ioremap() before it is used. */ if ((cfg->mem.nwin > 0) || (dflt.mem.nwin > 0)) { cistpl_mem_t *mem = (cfg->mem.nwin) ? &cfg->mem : &dflt.mem; req.Attributes = WIN_DATA_WIDTH_16|WIN_MEMORY_TYPE_CM; req.Attributes |= WIN_ENABLE; req.Base = mem->win[0].host_addr; req.Size = mem->win[0].len; /* new in dummy.cs 2001/01/28 MN if (req.Size < 0x1000) req.Size = 0x1000; */ req.AccessSpeed = 0; if (pcmcia_request_window(&link, &req, &link->win) != 0) goto next_entry; map.Page = 0; map.CardOffset = mem->win[0].card_addr; if (pcmcia_map_mem_page(link->win, &map) != 0) goto next_entry; if ((cfg->mem.nwin > 0) || (cfg_mem->dflt.mem.nwin > 0)) { cistpl_mem_t *mem = (cfg->mem.nwin) ? &cfg->mem : &cfg_mem->dflt.mem; memreq_t map; cfg_mem->req.Attributes = WIN_DATA_WIDTH_16|WIN_MEMORY_TYPE_CM; cfg_mem->req.Attributes |= WIN_ENABLE; cfg_mem->req.Base = mem->win[0].host_addr; cfg_mem->req.Size = mem->win[0].len; cfg_mem->req.AccessSpeed = 0; if (pcmcia_request_window(&p_dev, &cfg_mem->req, &p_dev->win) != 0) return -ENODEV; map.Page = 0; map.CardOffset = mem->win[0].card_addr; if (pcmcia_map_mem_page(p_dev->win, &map) != 0) return -ENODEV; } /* If we got this far, we're cool! */ break; next_entry: CS_CHECK(GetNextTuple, pcmcia_get_next_tuple(link, &tuple)); return 0; } static int sedlbauer_config(struct pcmcia_device *link) { local_info_t *dev = link->priv; struct sedlbauer_config_data *cfg_mem; int last_fn, last_ret; IsdnCard_t icard; DEBUG(0, "sedlbauer_config(0x%p)\n", link); cfg_mem = kzalloc(sizeof(struct sedlbauer_config_data), GFP_KERNEL); if (!cfg_mem) return -ENOMEM; /* Look up the current Vcc */ CS_CHECK(GetConfigurationInfo, pcmcia_get_configuration_info(link, &cfg_mem->conf)); /* In this loop, we scan the CIS for configuration table entries, each of which describes a valid card configuration, including voltage, IO window, memory window, and interrupt settings. We make no assumptions about the card to be configured: we use just the information available in the CIS. In an ideal world, this would work for any PCMCIA card, but it requires a complete and accurate CIS. In practice, a driver usually "knows" most of these things without consulting the CIS, and most client drivers will only use the CIS to fill in implementation-defined details. */ last_ret = pcmcia_loop_config(link, sedlbauer_config_check, cfg_mem); if (last_ret) goto failed; /* Allocate an interrupt line. Note that this does not assign a handler to the interrupt, unless the 'Handler' member of the Loading Loading @@ -387,8 +382,8 @@ static int sedlbauer_config(struct pcmcia_device *link) printk(" & 0x%04x-0x%04x", link->io.BasePort2, link->io.BasePort2+link->io.NumPorts2-1); if (link->win) printk(", mem 0x%06lx-0x%06lx", req.Base, req.Base+req.Size-1); printk(", mem 0x%06lx-0x%06lx", cfg_mem->req.Base, cfg_mem->req.Base+cfg_mem->req.Size-1); printk("\n"); icard.para[0] = link->irq.AssignedIRQ; Loading @@ -409,6 +404,7 @@ static int sedlbauer_config(struct pcmcia_device *link) cs_failed: cs_error(link, last_fn, last_ret); failed: sedlbauer_release(link); return -ENODEV; Loading drivers/isdn/hisax/teles_cs.c +23 −50 Original line number Diff line number Diff line Loading @@ -193,68 +193,41 @@ static void teles_detach(struct pcmcia_device *link) device available to the system. ======================================================================*/ static int get_tuple(struct pcmcia_device *handle, tuple_t *tuple, cisparse_t *parse) { int i = pcmcia_get_tuple_data(handle, tuple); if (i != CS_SUCCESS) return i; return pcmcia_parse_tuple(handle, tuple, parse); } static int first_tuple(struct pcmcia_device *handle, tuple_t *tuple, cisparse_t *parse) static int teles_cs_configcheck(struct pcmcia_device *p_dev, cistpl_cftable_entry_t *cf, void *priv_data) { int i = pcmcia_get_first_tuple(handle, tuple); if (i != CS_SUCCESS) return i; return get_tuple(handle, tuple, parse); } int j; static int next_tuple(struct pcmcia_device *handle, tuple_t *tuple, cisparse_t *parse) { int i = pcmcia_get_next_tuple(handle, tuple); if (i != CS_SUCCESS) return i; return get_tuple(handle, tuple, parse); if ((cf->io.nwin > 0) && cf->io.win[0].base) { printk(KERN_INFO "(teles_cs: looks like the 96 model)\n"); p_dev->conf.ConfigIndex = cf->index; p_dev->io.BasePort1 = cf->io.win[0].base; if (!pcmcia_request_io(p_dev, &p_dev->io)) return 0; } else { printk(KERN_INFO "(teles_cs: looks like the 97 model)\n"); p_dev->conf.ConfigIndex = cf->index; for (j = 0x2f0; j > 0x100; j -= 0x10) { p_dev->io.BasePort1 = j; if (!pcmcia_request_io(p_dev, &p_dev->io)) return 0; } } return -ENODEV; } static int teles_cs_config(struct pcmcia_device *link) { tuple_t tuple; cisparse_t parse; local_info_t *dev; int i, j, last_fn; u_short buf[128]; cistpl_cftable_entry_t *cf = &parse.cftable_entry; int i, last_fn; IsdnCard_t icard; DEBUG(0, "teles_config(0x%p)\n", link); dev = link->priv; tuple.TupleData = (cisdata_t *)buf; tuple.TupleOffset = 0; tuple.TupleDataMax = 255; tuple.Attributes = 0; tuple.DesiredTuple = CISTPL_CFTABLE_ENTRY; i = first_tuple(link, &tuple, &parse); while (i == CS_SUCCESS) { if ( (cf->io.nwin > 0) && cf->io.win[0].base) { printk(KERN_INFO "(teles_cs: looks like the 96 model)\n"); link->conf.ConfigIndex = cf->index; link->io.BasePort1 = cf->io.win[0].base; i = pcmcia_request_io(link, &link->io); if (i == CS_SUCCESS) break; } else { printk(KERN_INFO "(teles_cs: looks like the 97 model)\n"); link->conf.ConfigIndex = cf->index; for (i = 0, j = 0x2f0; j > 0x100; j -= 0x10) { link->io.BasePort1 = j; i = pcmcia_request_io(link, &link->io); if (i == CS_SUCCESS) break; } break; } i = next_tuple(link, &tuple, &parse); } i = pcmcia_loop_config(link, teles_cs_configcheck, NULL); if (i != CS_SUCCESS) { last_fn = RequestIO; goto cs_failed; Loading Loading
drivers/isdn/hardware/avm/avm_cs.c +23 −57 Original line number Diff line number Diff line Loading @@ -154,45 +154,33 @@ static void avmcs_detach(struct pcmcia_device *link) ======================================================================*/ static int get_tuple(struct pcmcia_device *handle, tuple_t *tuple, cisparse_t *parse) static int avmcs_configcheck(struct pcmcia_device *p_dev, cistpl_cftable_entry_t *cf, void *priv_data) { int i = pcmcia_get_tuple_data(handle, tuple); if (i != CS_SUCCESS) return i; return pcmcia_parse_tuple(handle, tuple, parse); } static int first_tuple(struct pcmcia_device *handle, tuple_t *tuple, cisparse_t *parse) { int i = pcmcia_get_first_tuple(handle, tuple); if (i != CS_SUCCESS) return i; return get_tuple(handle, tuple, parse); } if (cf->io.nwin <= 0) return -ENODEV; static int next_tuple(struct pcmcia_device *handle, tuple_t *tuple, cisparse_t *parse) { int i = pcmcia_get_next_tuple(handle, tuple); if (i != CS_SUCCESS) return i; return get_tuple(handle, tuple, parse); p_dev->conf.ConfigIndex = cf->index; p_dev->io.BasePort1 = cf->io.win[0].base; p_dev->io.NumPorts1 = cf->io.win[0].len; p_dev->io.NumPorts2 = 0; printk(KERN_INFO "avm_cs: testing i/o %#x-%#x\n", p_dev->io.BasePort1, p_dev->io.BasePort1+p_dev->io.NumPorts1-1); return pcmcia_request_io(p_dev, &p_dev->io); } static int avmcs_config(struct pcmcia_device *link) { tuple_t tuple; cisparse_t parse; cistpl_cftable_entry_t *cf = &parse.cftable_entry; local_info_t *dev; int i; u_char buf[64]; char devname[128]; int cardtype; int (*addcard)(unsigned int port, unsigned irq); dev = link->priv; do { devname[0] = 0; if (link->prod_id[1]) strlcpy(devname, link->prod_id[1], sizeof(devname)); Loading @@ -200,32 +188,10 @@ static int avmcs_config(struct pcmcia_device *link) /* * find IO port */ tuple.TupleData = (cisdata_t *)buf; tuple.TupleOffset = 0; tuple.TupleDataMax = 255; tuple.Attributes = 0; tuple.DesiredTuple = CISTPL_CFTABLE_ENTRY; i = first_tuple(link, &tuple, &parse); while (i == CS_SUCCESS) { if (cf->io.nwin > 0) { link->conf.ConfigIndex = cf->index; link->io.BasePort1 = cf->io.win[0].base; link->io.NumPorts1 = cf->io.win[0].len; link->io.NumPorts2 = 0; printk(KERN_INFO "avm_cs: testing i/o %#x-%#x\n", link->io.BasePort1, link->io.BasePort1+link->io.NumPorts1-1); i = pcmcia_request_io(link, &link->io); if (i == CS_SUCCESS) goto found_port; } i = next_tuple(link, &tuple, &parse); } found_port: if (i != CS_SUCCESS) { cs_error(link, RequestIO, i); break; } if (pcmcia_loop_config(link, avmcs_configcheck, NULL)) return -ENODEV; do { /* * allocate an interrupt line */ Loading
drivers/isdn/hisax/avma1_cs.c +20 −56 Original line number Diff line number Diff line Loading @@ -174,38 +174,28 @@ static void avma1cs_detach(struct pcmcia_device *link) ======================================================================*/ static int get_tuple(struct pcmcia_device *handle, tuple_t *tuple, cisparse_t *parse) static int avma1cs_configcheck(struct pcmcia_device *p_dev, cistpl_cftable_entry_t *cf, void *priv_data) { int i = pcmcia_get_tuple_data(handle, tuple); if (i != CS_SUCCESS) return i; return pcmcia_parse_tuple(handle, tuple, parse); } if (cf->io.nwin <= 0) return -ENODEV; static int first_tuple(struct pcmcia_device *handle, tuple_t *tuple, cisparse_t *parse) { int i = pcmcia_get_first_tuple(handle, tuple); if (i != CS_SUCCESS) return i; return get_tuple(handle, tuple, parse); p_dev->conf.ConfigIndex = cf->index; p_dev->io.BasePort1 = cf->io.win[0].base; p_dev->io.NumPorts1 = cf->io.win[0].len; p_dev->io.NumPorts2 = 0; printk(KERN_INFO "avma1_cs: testing i/o %#x-%#x\n", p_dev->io.BasePort1, p_dev->io.BasePort1+p_dev->io.NumPorts1-1); return pcmcia_request_io(p_dev, &p_dev->io); } static int next_tuple(struct pcmcia_device *handle, tuple_t *tuple, cisparse_t *parse) { int i = pcmcia_get_next_tuple(handle, tuple); if (i != CS_SUCCESS) return i; return get_tuple(handle, tuple, parse); } static int avma1cs_config(struct pcmcia_device *link) { tuple_t tuple; cisparse_t parse; cistpl_cftable_entry_t *cf = &parse.cftable_entry; local_info_t *dev; int i; u_char buf[64]; char devname[128]; IsdnCard_t icard; int busy = 0; Loading @@ -214,40 +204,14 @@ static int avma1cs_config(struct pcmcia_device *link) DEBUG(0, "avma1cs_config(0x%p)\n", link); do { devname[0] = 0; if (link->prod_id[1]) strlcpy(devname, link->prod_id[1], sizeof(devname)); /* * find IO port */ tuple.TupleData = (cisdata_t *)buf; tuple.TupleOffset = 0; tuple.TupleDataMax = 255; tuple.Attributes = 0; tuple.DesiredTuple = CISTPL_CFTABLE_ENTRY; i = first_tuple(link, &tuple, &parse); while (i == CS_SUCCESS) { if (cf->io.nwin > 0) { link->conf.ConfigIndex = cf->index; link->io.BasePort1 = cf->io.win[0].base; link->io.NumPorts1 = cf->io.win[0].len; link->io.NumPorts2 = 0; printk(KERN_INFO "avma1_cs: testing i/o %#x-%#x\n", link->io.BasePort1, link->io.BasePort1+link->io.NumPorts1 - 1); i = pcmcia_request_io(link, &link->io); if (i == CS_SUCCESS) goto found_port; } i = next_tuple(link, &tuple, &parse); } found_port: if (i != CS_SUCCESS) { cs_error(link, RequestIO, i); break; } if (pcmcia_loop_config(link, avma1cs_configcheck, NULL)) return -ENODEV; do { /* * allocate an interrupt line */ Loading
drivers/isdn/hisax/elsa_cs.c +23 −50 Original line number Diff line number Diff line Loading @@ -203,68 +203,41 @@ static void elsa_cs_detach(struct pcmcia_device *link) device available to the system. ======================================================================*/ static int get_tuple(struct pcmcia_device *handle, tuple_t *tuple, cisparse_t *parse) { int i = pcmcia_get_tuple_data(handle, tuple); if (i != CS_SUCCESS) return i; return pcmcia_parse_tuple(handle, tuple, parse); } static int first_tuple(struct pcmcia_device *handle, tuple_t *tuple, cisparse_t *parse) static int elsa_cs_configcheck(struct pcmcia_device *p_dev, cistpl_cftable_entry_t *cf, void *priv_data) { int i = pcmcia_get_first_tuple(handle, tuple); if (i != CS_SUCCESS) return i; return get_tuple(handle, tuple, parse); } int j; static int next_tuple(struct pcmcia_device *handle, tuple_t *tuple, cisparse_t *parse) { int i = pcmcia_get_next_tuple(handle, tuple); if (i != CS_SUCCESS) return i; return get_tuple(handle, tuple, parse); if ((cf->io.nwin > 0) && cf->io.win[0].base) { printk(KERN_INFO "(elsa_cs: looks like the 96 model)\n"); p_dev->conf.ConfigIndex = cf->index; p_dev->io.BasePort1 = cf->io.win[0].base; if (!pcmcia_request_io(p_dev, &p_dev->io)) return 0; } else { printk(KERN_INFO "(elsa_cs: looks like the 97 model)\n"); p_dev->conf.ConfigIndex = cf->index; for (j = 0x2f0; j > 0x100; j -= 0x10) { p_dev->io.BasePort1 = j; if (!pcmcia_request_io(p_dev, &p_dev->io)) return 0; } } return -ENODEV; } static int elsa_cs_config(struct pcmcia_device *link) { tuple_t tuple; cisparse_t parse; local_info_t *dev; int i, j, last_fn; u_short buf[128]; cistpl_cftable_entry_t *cf = &parse.cftable_entry; int i, last_fn; IsdnCard_t icard; DEBUG(0, "elsa_config(0x%p)\n", link); dev = link->priv; tuple.TupleData = (cisdata_t *)buf; tuple.TupleOffset = 0; tuple.TupleDataMax = 255; tuple.Attributes = 0; tuple.DesiredTuple = CISTPL_CFTABLE_ENTRY; i = first_tuple(link, &tuple, &parse); while (i == CS_SUCCESS) { if ( (cf->io.nwin > 0) && cf->io.win[0].base) { printk(KERN_INFO "(elsa_cs: looks like the 96 model)\n"); link->conf.ConfigIndex = cf->index; link->io.BasePort1 = cf->io.win[0].base; i = pcmcia_request_io(link, &link->io); if (i == CS_SUCCESS) break; } else { printk(KERN_INFO "(elsa_cs: looks like the 97 model)\n"); link->conf.ConfigIndex = cf->index; for (i = 0, j = 0x2f0; j > 0x100; j -= 0x10) { link->io.BasePort1 = j; i = pcmcia_request_io(link, &link->io); if (i == CS_SUCCESS) break; } break; } i = next_tuple(link, &tuple, &parse); } i = pcmcia_loop_config(link, elsa_cs_configcheck, NULL); if (i != CS_SUCCESS) { last_fn = RequestIO; goto cs_failed; Loading
drivers/isdn/hisax/sedlbauer_cs.c +102 −106 Original line number Diff line number Diff line Loading @@ -217,101 +217,68 @@ static void sedlbauer_detach(struct pcmcia_device *link) #define CS_CHECK(fn, ret) \ do { last_fn = (fn); if ((last_ret = (ret)) != 0) goto cs_failed; } while (0) static int sedlbauer_config(struct pcmcia_device *link) { local_info_t *dev = link->priv; tuple_t tuple; cisparse_t parse; int last_fn, last_ret; u8 buf[64]; struct sedlbauer_config_data { cistpl_cftable_entry_t dflt; config_info_t conf; win_req_t req; memreq_t map; IsdnCard_t icard; DEBUG(0, "sedlbauer_config(0x%p)\n", link); tuple.Attributes = 0; tuple.TupleData = buf; tuple.TupleDataMax = sizeof(buf); tuple.TupleOffset = 0; CS_CHECK(GetConfigurationInfo, pcmcia_get_configuration_info(link, &conf)); }; /* In this loop, we scan the CIS for configuration table entries, each of which describes a valid card configuration, including voltage, IO window, memory window, and interrupt settings. static int sedlbauer_config_check(struct pcmcia_device *p_dev, cistpl_cftable_entry_t *cfg, void *priv_data) { struct sedlbauer_config_data *cfg_mem = priv_data; We make no assumptions about the card to be configured: we use just the information available in the CIS. In an ideal world, this would work for any PCMCIA card, but it requires a complete and accurate CIS. In practice, a driver usually "knows" most of these things without consulting the CIS, and most client drivers will only use the CIS to fill in implementation-defined details. */ tuple.DesiredTuple = CISTPL_CFTABLE_ENTRY; CS_CHECK(GetFirstTuple, pcmcia_get_first_tuple(link, &tuple)); while (1) { cistpl_cftable_entry_t dflt = { 0 }; cistpl_cftable_entry_t *cfg = &(parse.cftable_entry); if (pcmcia_get_tuple_data(link, &tuple) != 0 || pcmcia_parse_tuple(link, &tuple, &parse) != 0) goto next_entry; if (cfg->flags & CISTPL_CFTABLE_DEFAULT) dflt = *cfg; if (cfg->index == 0) goto next_entry; link->conf.ConfigIndex = cfg->index; if (cfg->flags & CISTPL_CFTABLE_DEFAULT) cfg_mem->dflt = *cfg; if (cfg->index == 0) return -ENODEV; p_dev->conf.ConfigIndex = cfg->index; /* Does this card need audio output? */ if (cfg->flags & CISTPL_CFTABLE_AUDIO) { link->conf.Attributes |= CONF_ENABLE_SPKR; link->conf.Status = CCSR_AUDIO_ENA; p_dev->conf.Attributes |= CONF_ENABLE_SPKR; p_dev->conf.Status = CCSR_AUDIO_ENA; } /* Use power settings for Vcc and Vpp if present */ /* Note that the CIS values need to be rescaled */ if (cfg->vcc.present & (1<<CISTPL_POWER_VNOM)) { if (conf.Vcc != cfg->vcc.param[CISTPL_POWER_VNOM]/10000) goto next_entry; } else if (dflt.vcc.present & (1<<CISTPL_POWER_VNOM)) { if (conf.Vcc != dflt.vcc.param[CISTPL_POWER_VNOM]/10000) goto next_entry; if (cfg_mem->conf.Vcc != cfg->vcc.param[CISTPL_POWER_VNOM]/10000) return -ENODEV; } else if (cfg_mem->dflt.vcc.present & (1<<CISTPL_POWER_VNOM)) { if (cfg_mem->conf.Vcc != cfg_mem->dflt.vcc.param[CISTPL_POWER_VNOM]/10000) return -ENODEV; } if (cfg->vpp1.present & (1<<CISTPL_POWER_VNOM)) link->conf.Vpp = cfg->vpp1.param[CISTPL_POWER_VNOM]/10000; else if (dflt.vpp1.present & (1<<CISTPL_POWER_VNOM)) link->conf.Vpp = dflt.vpp1.param[CISTPL_POWER_VNOM]/10000; p_dev->conf.Vpp = cfg->vpp1.param[CISTPL_POWER_VNOM]/10000; else if (cfg_mem->dflt.vpp1.present & (1<<CISTPL_POWER_VNOM)) p_dev->conf.Vpp = cfg_mem->dflt.vpp1.param[CISTPL_POWER_VNOM]/10000; /* Do we need to allocate an interrupt? */ if (cfg->irq.IRQInfo1 || dflt.irq.IRQInfo1) link->conf.Attributes |= CONF_ENABLE_IRQ; if (cfg->irq.IRQInfo1 || cfg_mem->dflt.irq.IRQInfo1) p_dev->conf.Attributes |= CONF_ENABLE_IRQ; /* IO window settings */ link->io.NumPorts1 = link->io.NumPorts2 = 0; if ((cfg->io.nwin > 0) || (dflt.io.nwin > 0)) { cistpl_io_t *io = (cfg->io.nwin) ? &cfg->io : &dflt.io; link->io.Attributes1 = IO_DATA_PATH_WIDTH_AUTO; p_dev->io.NumPorts1 = p_dev->io.NumPorts2 = 0; if ((cfg->io.nwin > 0) || (cfg_mem->dflt.io.nwin > 0)) { cistpl_io_t *io = (cfg->io.nwin) ? &cfg->io : &cfg_mem->dflt.io; p_dev->io.Attributes1 = IO_DATA_PATH_WIDTH_AUTO; if (!(io->flags & CISTPL_IO_8BIT)) link->io.Attributes1 = IO_DATA_PATH_WIDTH_16; p_dev->io.Attributes1 = IO_DATA_PATH_WIDTH_16; if (!(io->flags & CISTPL_IO_16BIT)) link->io.Attributes1 = IO_DATA_PATH_WIDTH_8; /* new in dummy.cs 2001/01/28 MN link->io.IOAddrLines = io->flags & CISTPL_IO_LINES_MASK; */ link->io.BasePort1 = io->win[0].base; link->io.NumPorts1 = io->win[0].len; p_dev->io.Attributes1 = IO_DATA_PATH_WIDTH_8; p_dev->io.BasePort1 = io->win[0].base; p_dev->io.NumPorts1 = io->win[0].len; if (io->nwin > 1) { link->io.Attributes2 = link->io.Attributes1; link->io.BasePort2 = io->win[1].base; link->io.NumPorts2 = io->win[1].len; p_dev->io.Attributes2 = p_dev->io.Attributes1; p_dev->io.BasePort2 = io->win[1].base; p_dev->io.NumPorts2 = io->win[1].len; } /* This reserves IO space but doesn't actually enable it */ if (pcmcia_request_io(link, &link->io) != 0) goto next_entry; if (pcmcia_request_io(p_dev, &p_dev->io) != 0) return -ENODEV; } /* Loading @@ -325,31 +292,59 @@ static int sedlbauer_config(struct pcmcia_device *link) needs to be mapped to virtual space with ioremap() before it is used. */ if ((cfg->mem.nwin > 0) || (dflt.mem.nwin > 0)) { cistpl_mem_t *mem = (cfg->mem.nwin) ? &cfg->mem : &dflt.mem; req.Attributes = WIN_DATA_WIDTH_16|WIN_MEMORY_TYPE_CM; req.Attributes |= WIN_ENABLE; req.Base = mem->win[0].host_addr; req.Size = mem->win[0].len; /* new in dummy.cs 2001/01/28 MN if (req.Size < 0x1000) req.Size = 0x1000; */ req.AccessSpeed = 0; if (pcmcia_request_window(&link, &req, &link->win) != 0) goto next_entry; map.Page = 0; map.CardOffset = mem->win[0].card_addr; if (pcmcia_map_mem_page(link->win, &map) != 0) goto next_entry; if ((cfg->mem.nwin > 0) || (cfg_mem->dflt.mem.nwin > 0)) { cistpl_mem_t *mem = (cfg->mem.nwin) ? &cfg->mem : &cfg_mem->dflt.mem; memreq_t map; cfg_mem->req.Attributes = WIN_DATA_WIDTH_16|WIN_MEMORY_TYPE_CM; cfg_mem->req.Attributes |= WIN_ENABLE; cfg_mem->req.Base = mem->win[0].host_addr; cfg_mem->req.Size = mem->win[0].len; cfg_mem->req.AccessSpeed = 0; if (pcmcia_request_window(&p_dev, &cfg_mem->req, &p_dev->win) != 0) return -ENODEV; map.Page = 0; map.CardOffset = mem->win[0].card_addr; if (pcmcia_map_mem_page(p_dev->win, &map) != 0) return -ENODEV; } /* If we got this far, we're cool! */ break; next_entry: CS_CHECK(GetNextTuple, pcmcia_get_next_tuple(link, &tuple)); return 0; } static int sedlbauer_config(struct pcmcia_device *link) { local_info_t *dev = link->priv; struct sedlbauer_config_data *cfg_mem; int last_fn, last_ret; IsdnCard_t icard; DEBUG(0, "sedlbauer_config(0x%p)\n", link); cfg_mem = kzalloc(sizeof(struct sedlbauer_config_data), GFP_KERNEL); if (!cfg_mem) return -ENOMEM; /* Look up the current Vcc */ CS_CHECK(GetConfigurationInfo, pcmcia_get_configuration_info(link, &cfg_mem->conf)); /* In this loop, we scan the CIS for configuration table entries, each of which describes a valid card configuration, including voltage, IO window, memory window, and interrupt settings. We make no assumptions about the card to be configured: we use just the information available in the CIS. In an ideal world, this would work for any PCMCIA card, but it requires a complete and accurate CIS. In practice, a driver usually "knows" most of these things without consulting the CIS, and most client drivers will only use the CIS to fill in implementation-defined details. */ last_ret = pcmcia_loop_config(link, sedlbauer_config_check, cfg_mem); if (last_ret) goto failed; /* Allocate an interrupt line. Note that this does not assign a handler to the interrupt, unless the 'Handler' member of the Loading Loading @@ -387,8 +382,8 @@ static int sedlbauer_config(struct pcmcia_device *link) printk(" & 0x%04x-0x%04x", link->io.BasePort2, link->io.BasePort2+link->io.NumPorts2-1); if (link->win) printk(", mem 0x%06lx-0x%06lx", req.Base, req.Base+req.Size-1); printk(", mem 0x%06lx-0x%06lx", cfg_mem->req.Base, cfg_mem->req.Base+cfg_mem->req.Size-1); printk("\n"); icard.para[0] = link->irq.AssignedIRQ; Loading @@ -409,6 +404,7 @@ static int sedlbauer_config(struct pcmcia_device *link) cs_failed: cs_error(link, last_fn, last_ret); failed: sedlbauer_release(link); return -ENODEV; Loading
drivers/isdn/hisax/teles_cs.c +23 −50 Original line number Diff line number Diff line Loading @@ -193,68 +193,41 @@ static void teles_detach(struct pcmcia_device *link) device available to the system. ======================================================================*/ static int get_tuple(struct pcmcia_device *handle, tuple_t *tuple, cisparse_t *parse) { int i = pcmcia_get_tuple_data(handle, tuple); if (i != CS_SUCCESS) return i; return pcmcia_parse_tuple(handle, tuple, parse); } static int first_tuple(struct pcmcia_device *handle, tuple_t *tuple, cisparse_t *parse) static int teles_cs_configcheck(struct pcmcia_device *p_dev, cistpl_cftable_entry_t *cf, void *priv_data) { int i = pcmcia_get_first_tuple(handle, tuple); if (i != CS_SUCCESS) return i; return get_tuple(handle, tuple, parse); } int j; static int next_tuple(struct pcmcia_device *handle, tuple_t *tuple, cisparse_t *parse) { int i = pcmcia_get_next_tuple(handle, tuple); if (i != CS_SUCCESS) return i; return get_tuple(handle, tuple, parse); if ((cf->io.nwin > 0) && cf->io.win[0].base) { printk(KERN_INFO "(teles_cs: looks like the 96 model)\n"); p_dev->conf.ConfigIndex = cf->index; p_dev->io.BasePort1 = cf->io.win[0].base; if (!pcmcia_request_io(p_dev, &p_dev->io)) return 0; } else { printk(KERN_INFO "(teles_cs: looks like the 97 model)\n"); p_dev->conf.ConfigIndex = cf->index; for (j = 0x2f0; j > 0x100; j -= 0x10) { p_dev->io.BasePort1 = j; if (!pcmcia_request_io(p_dev, &p_dev->io)) return 0; } } return -ENODEV; } static int teles_cs_config(struct pcmcia_device *link) { tuple_t tuple; cisparse_t parse; local_info_t *dev; int i, j, last_fn; u_short buf[128]; cistpl_cftable_entry_t *cf = &parse.cftable_entry; int i, last_fn; IsdnCard_t icard; DEBUG(0, "teles_config(0x%p)\n", link); dev = link->priv; tuple.TupleData = (cisdata_t *)buf; tuple.TupleOffset = 0; tuple.TupleDataMax = 255; tuple.Attributes = 0; tuple.DesiredTuple = CISTPL_CFTABLE_ENTRY; i = first_tuple(link, &tuple, &parse); while (i == CS_SUCCESS) { if ( (cf->io.nwin > 0) && cf->io.win[0].base) { printk(KERN_INFO "(teles_cs: looks like the 96 model)\n"); link->conf.ConfigIndex = cf->index; link->io.BasePort1 = cf->io.win[0].base; i = pcmcia_request_io(link, &link->io); if (i == CS_SUCCESS) break; } else { printk(KERN_INFO "(teles_cs: looks like the 97 model)\n"); link->conf.ConfigIndex = cf->index; for (i = 0, j = 0x2f0; j > 0x100; j -= 0x10) { link->io.BasePort1 = j; i = pcmcia_request_io(link, &link->io); if (i == CS_SUCCESS) break; } break; } i = next_tuple(link, &tuple, &parse); } i = pcmcia_loop_config(link, teles_cs_configcheck, NULL); if (i != CS_SUCCESS) { last_fn = RequestIO; goto cs_failed; Loading