pcmcia: introduce autoconfiguration feature
Introduce an autoconfiguration feature to set certain values in pcmcia_loop_config(), instead of copying the same code over and over in each PCMCIA driver. At first, introduce the following options: CONF_AUTO_CHECK_VCC check or matching Vcc entry CONF_AUTO_SET_VPP set Vpp CONF_AUTO_AUDIO enable the speaker line CC: netdev@vger.kernel.org CC: linux-wireless@vger.kernel.org CC: linux-ide@vger.kernel.org CC: linux-usb@vger.kernel.org CC: laforge@gnumonks.org CC: linux-mtd@lists.infradead.org CC: alsa-devel@alsa-project.org CC: linux-serial@vger.kernel.org CC: Jiri Kosina <jkosina@suse.cz> CC: linux-scsi@vger.kernel.org Acked-by: Gustavo F. Padovan <padovan@profusion.mobi> (for drivers/bluetooth) Tested-by: Wolfram Sang <w.sang@pengutronix.de> Signed-off-by: Dominik Brodowski <linux@dominikbrodowski.net>
This commit is contained in:
parent
9485ee14e1
commit
440eed43e2
43 changed files with 122 additions and 331 deletions
|
@ -169,34 +169,16 @@ static struct ata_port_operations pcmcia_8bit_port_ops = {
|
|||
|
||||
struct pcmcia_config_check {
|
||||
unsigned long ctl_base;
|
||||
int skip_vcc;
|
||||
int is_kme;
|
||||
};
|
||||
|
||||
static int pcmcia_check_one_config(struct pcmcia_device *pdev,
|
||||
cistpl_cftable_entry_t *cfg,
|
||||
cistpl_cftable_entry_t *dflt,
|
||||
unsigned int vcc,
|
||||
void *priv_data)
|
||||
{
|
||||
struct pcmcia_config_check *stk = priv_data;
|
||||
|
||||
/* Check for matching Vcc, unless we're desperate */
|
||||
if (!stk->skip_vcc) {
|
||||
if (cfg->vcc.present & (1 << CISTPL_POWER_VNOM)) {
|
||||
if (vcc != cfg->vcc.param[CISTPL_POWER_VNOM] / 10000)
|
||||
return -ENODEV;
|
||||
} else if (dflt->vcc.present & (1 << CISTPL_POWER_VNOM)) {
|
||||
if (vcc != dflt->vcc.param[CISTPL_POWER_VNOM] / 10000)
|
||||
return -ENODEV;
|
||||
}
|
||||
}
|
||||
|
||||
if (cfg->vpp1.present & (1 << CISTPL_POWER_VNOM))
|
||||
pdev->vpp = cfg->vpp1.param[CISTPL_POWER_VNOM] / 10000;
|
||||
else if (dflt->vpp1.present & (1 << CISTPL_POWER_VNOM))
|
||||
pdev->vpp = dflt->vpp1.param[CISTPL_POWER_VNOM] / 10000;
|
||||
|
||||
if ((cfg->io.nwin > 0) || (dflt->io.nwin > 0)) {
|
||||
cistpl_io_t *io = (cfg->io.nwin) ? &cfg->io : &dflt->io;
|
||||
pdev->io_lines = io->flags & CISTPL_IO_LINES_MASK;
|
||||
|
@ -249,6 +231,7 @@ static int pcmcia_init_one(struct pcmcia_device *pdev)
|
|||
pdev->resource[0]->flags |= IO_DATA_PATH_WIDTH_AUTO;
|
||||
pdev->resource[1]->flags |= IO_DATA_PATH_WIDTH_8;
|
||||
pdev->config_flags |= CONF_ENABLE_IRQ;
|
||||
pdev->config_flags |= CONF_AUTO_SET_VPP | CONF_AUTO_CHECK_VCC;
|
||||
|
||||
/* See if we have a manufacturer identifier. Use it to set is_kme for
|
||||
vendor quirks */
|
||||
|
@ -262,10 +245,10 @@ static int pcmcia_init_one(struct pcmcia_device *pdev)
|
|||
if (!stk)
|
||||
goto out1;
|
||||
stk->is_kme = is_kme;
|
||||
stk->skip_vcc = io_base = ctl_base = 0;
|
||||
io_base = ctl_base = 0;
|
||||
|
||||
if (pcmcia_loop_config(pdev, pcmcia_check_one_config, stk)) {
|
||||
stk->skip_vcc = 1;
|
||||
pdev->config_flags &= ~CONF_AUTO_CHECK_VCC;
|
||||
if (pcmcia_loop_config(pdev, pcmcia_check_one_config, stk))
|
||||
goto failed; /* No suitable config found */
|
||||
}
|
||||
|
|
|
@ -659,7 +659,7 @@ static int bt3c_probe(struct pcmcia_device *link)
|
|||
link->resource[0]->flags |= IO_DATA_PATH_WIDTH_8;
|
||||
link->resource[0]->end = 8;
|
||||
|
||||
link->config_flags |= CONF_ENABLE_IRQ;
|
||||
link->config_flags |= CONF_ENABLE_IRQ | CONF_AUTO_SET_VPP;
|
||||
|
||||
return bt3c_config(link);
|
||||
}
|
||||
|
@ -676,15 +676,11 @@ static void bt3c_detach(struct pcmcia_device *link)
|
|||
static int bt3c_check_config(struct pcmcia_device *p_dev,
|
||||
cistpl_cftable_entry_t *cf,
|
||||
cistpl_cftable_entry_t *dflt,
|
||||
unsigned int vcc,
|
||||
void *priv_data)
|
||||
{
|
||||
unsigned long try = (unsigned long) priv_data;
|
||||
|
||||
p_dev->io_lines = (try == 0) ? 16 : cf->io.flags & CISTPL_IO_LINES_MASK;
|
||||
|
||||
if (cf->vpp1.present & (1 << CISTPL_POWER_VNOM))
|
||||
p_dev->vpp = cf->vpp1.param[CISTPL_POWER_VNOM] / 10000;
|
||||
if ((cf->io.nwin > 0) && (cf->io.win[0].len == 8) &&
|
||||
(cf->io.win[0].base != 0)) {
|
||||
p_dev->resource[0]->start = cf->io.win[0].base;
|
||||
|
@ -697,7 +693,6 @@ static int bt3c_check_config(struct pcmcia_device *p_dev,
|
|||
static int bt3c_check_config_notpicky(struct pcmcia_device *p_dev,
|
||||
cistpl_cftable_entry_t *cf,
|
||||
cistpl_cftable_entry_t *dflt,
|
||||
unsigned int vcc,
|
||||
void *priv_data)
|
||||
{
|
||||
static unsigned int base[5] = { 0x3f8, 0x2f8, 0x3e8, 0x2e8, 0x0 };
|
||||
|
|
|
@ -588,7 +588,7 @@ static int btuart_probe(struct pcmcia_device *link)
|
|||
link->resource[0]->flags |= IO_DATA_PATH_WIDTH_8;
|
||||
link->resource[0]->end = 8;
|
||||
|
||||
link->config_flags |= CONF_ENABLE_IRQ;
|
||||
link->config_flags |= CONF_ENABLE_IRQ | CONF_AUTO_SET_VPP;
|
||||
|
||||
return btuart_config(link);
|
||||
}
|
||||
|
@ -605,15 +605,11 @@ static void btuart_detach(struct pcmcia_device *link)
|
|||
static int btuart_check_config(struct pcmcia_device *p_dev,
|
||||
cistpl_cftable_entry_t *cf,
|
||||
cistpl_cftable_entry_t *dflt,
|
||||
unsigned int vcc,
|
||||
void *priv_data)
|
||||
{
|
||||
int *try = priv_data;
|
||||
|
||||
p_dev->io_lines = (try == 0) ? 16 : cf->io.flags & CISTPL_IO_LINES_MASK;
|
||||
|
||||
if (cf->vpp1.present & (1 << CISTPL_POWER_VNOM))
|
||||
p_dev->vpp = cf->vpp1.param[CISTPL_POWER_VNOM] / 10000;
|
||||
if ((cf->io.nwin > 0) && (cf->io.win[0].len == 8) &&
|
||||
(cf->io.win[0].base != 0)) {
|
||||
p_dev->resource[0]->start = cf->io.win[0].base;
|
||||
|
@ -626,7 +622,6 @@ static int btuart_check_config(struct pcmcia_device *p_dev,
|
|||
static int btuart_check_config_notpicky(struct pcmcia_device *p_dev,
|
||||
cistpl_cftable_entry_t *cf,
|
||||
cistpl_cftable_entry_t *dflt,
|
||||
unsigned int vcc,
|
||||
void *priv_data)
|
||||
{
|
||||
static unsigned int base[5] = { 0x3f8, 0x2f8, 0x3e8, 0x2e8, 0x0 };
|
||||
|
|
|
@ -592,7 +592,6 @@ static void dtl1_detach(struct pcmcia_device *link)
|
|||
static int dtl1_confcheck(struct pcmcia_device *p_dev,
|
||||
cistpl_cftable_entry_t *cf,
|
||||
cistpl_cftable_entry_t *dflt,
|
||||
unsigned int vcc,
|
||||
void *priv_data)
|
||||
{
|
||||
if ((cf->io.nwin != 1) || (cf->io.win[0].len <= 8))
|
||||
|
|
|
@ -1744,7 +1744,6 @@ static void cmm_cm4000_release(struct pcmcia_device * link)
|
|||
static int cm4000_config_check(struct pcmcia_device *p_dev,
|
||||
cistpl_cftable_entry_t *cfg,
|
||||
cistpl_cftable_entry_t *dflt,
|
||||
unsigned int vcc,
|
||||
void *priv_data)
|
||||
{
|
||||
if (!cfg->io.nwin)
|
||||
|
|
|
@ -518,7 +518,6 @@ static void cm4040_reader_release(struct pcmcia_device *link)
|
|||
static int cm4040_config_check(struct pcmcia_device *p_dev,
|
||||
cistpl_cftable_entry_t *cfg,
|
||||
cistpl_cftable_entry_t *dflt,
|
||||
unsigned int vcc,
|
||||
void *priv_data)
|
||||
{
|
||||
int rc;
|
||||
|
|
|
@ -78,7 +78,6 @@ static void signalled_reboot_callback(void *callback_data)
|
|||
static int ipwireless_probe(struct pcmcia_device *p_dev,
|
||||
cistpl_cftable_entry_t *cfg,
|
||||
cistpl_cftable_entry_t *dflt,
|
||||
unsigned int vcc,
|
||||
void *priv_data)
|
||||
{
|
||||
struct ipw_dev *ipw = priv_data;
|
||||
|
|
|
@ -564,7 +564,6 @@ static int mgslpc_probe(struct pcmcia_device *link)
|
|||
static int mgslpc_ioprobe(struct pcmcia_device *p_dev,
|
||||
cistpl_cftable_entry_t *cfg,
|
||||
cistpl_cftable_entry_t *dflt,
|
||||
unsigned int vcc,
|
||||
void *priv_data)
|
||||
{
|
||||
if (!cfg->io.nwin)
|
||||
|
|
|
@ -99,6 +99,7 @@ static int ide_probe(struct pcmcia_device *link)
|
|||
link->resource[0]->flags |= IO_DATA_PATH_WIDTH_AUTO;
|
||||
link->resource[1]->flags |= IO_DATA_PATH_WIDTH_8;
|
||||
link->config_flags |= CONF_ENABLE_IRQ;
|
||||
link->config_flags |= CONF_AUTO_SET_VPP | CONF_AUTO_CHECK_VCC;
|
||||
|
||||
return ide_config(link);
|
||||
} /* ide_attach */
|
||||
|
@ -195,34 +196,16 @@ out_release:
|
|||
|
||||
struct pcmcia_config_check {
|
||||
unsigned long ctl_base;
|
||||
int skip_vcc;
|
||||
int is_kme;
|
||||
};
|
||||
|
||||
static int pcmcia_check_one_config(struct pcmcia_device *pdev,
|
||||
cistpl_cftable_entry_t *cfg,
|
||||
cistpl_cftable_entry_t *dflt,
|
||||
unsigned int vcc,
|
||||
void *priv_data)
|
||||
{
|
||||
struct pcmcia_config_check *stk = priv_data;
|
||||
|
||||
/* Check for matching Vcc, unless we're desperate */
|
||||
if (!stk->skip_vcc) {
|
||||
if (cfg->vcc.present & (1 << CISTPL_POWER_VNOM)) {
|
||||
if (vcc != cfg->vcc.param[CISTPL_POWER_VNOM] / 10000)
|
||||
return -ENODEV;
|
||||
} else if (dflt->vcc.present & (1 << CISTPL_POWER_VNOM)) {
|
||||
if (vcc != dflt->vcc.param[CISTPL_POWER_VNOM] / 10000)
|
||||
return -ENODEV;
|
||||
}
|
||||
}
|
||||
|
||||
if (cfg->vpp1.present & (1 << CISTPL_POWER_VNOM))
|
||||
pdev->vpp = cfg->vpp1.param[CISTPL_POWER_VNOM] / 10000;
|
||||
else if (dflt->vpp1.present & (1 << CISTPL_POWER_VNOM))
|
||||
pdev->vpp = dflt->vpp1.param[CISTPL_POWER_VNOM] / 10000;
|
||||
|
||||
if ((cfg->io.nwin > 0) || (dflt->io.nwin > 0)) {
|
||||
cistpl_io_t *io = (cfg->io.nwin) ? &cfg->io : &dflt->io;
|
||||
pdev->io_lines = io->flags & CISTPL_IO_LINES_MASK;
|
||||
|
@ -271,10 +254,10 @@ static int ide_config(struct pcmcia_device *link)
|
|||
if (!stk)
|
||||
goto err_mem;
|
||||
stk->is_kme = is_kme;
|
||||
stk->skip_vcc = io_base = ctl_base = 0;
|
||||
io_base = ctl_base = 0;
|
||||
|
||||
if (pcmcia_loop_config(link, pcmcia_check_one_config, stk)) {
|
||||
stk->skip_vcc = 1;
|
||||
link->config_flags &= ~CONF_AUTO_CHECK_VCC;
|
||||
if (pcmcia_loop_config(link, pcmcia_check_one_config, stk))
|
||||
goto failed; /* No suitable config found */
|
||||
}
|
||||
|
|
|
@ -110,7 +110,6 @@ static void avmcs_detach(struct pcmcia_device *link)
|
|||
static int avmcs_configcheck(struct pcmcia_device *p_dev,
|
||||
cistpl_cftable_entry_t *cf,
|
||||
cistpl_cftable_entry_t *dflt,
|
||||
unsigned int vcc,
|
||||
void *priv_data)
|
||||
{
|
||||
if (cf->io.nwin <= 0)
|
||||
|
|
|
@ -117,7 +117,6 @@ static void __devexit avma1cs_detach(struct pcmcia_device *link)
|
|||
static int avma1cs_configcheck(struct pcmcia_device *p_dev,
|
||||
cistpl_cftable_entry_t *cf,
|
||||
cistpl_cftable_entry_t *dflt,
|
||||
unsigned int vcc,
|
||||
void *priv_data)
|
||||
{
|
||||
if (cf->io.nwin <= 0)
|
||||
|
|
|
@ -163,7 +163,6 @@ static void __devexit elsa_cs_detach(struct pcmcia_device *link)
|
|||
static int elsa_cs_configcheck(struct pcmcia_device *p_dev,
|
||||
cistpl_cftable_entry_t *cf,
|
||||
cistpl_cftable_entry_t *dflt,
|
||||
unsigned int vcc,
|
||||
void *priv_data)
|
||||
{
|
||||
int j;
|
||||
|
|
|
@ -164,33 +164,11 @@ static void __devexit sedlbauer_detach(struct pcmcia_device *link)
|
|||
static int sedlbauer_config_check(struct pcmcia_device *p_dev,
|
||||
cistpl_cftable_entry_t *cfg,
|
||||
cistpl_cftable_entry_t *dflt,
|
||||
unsigned int vcc,
|
||||
void *priv_data)
|
||||
{
|
||||
if (cfg->index == 0)
|
||||
return -ENODEV;
|
||||
|
||||
/* Does this card need audio output? */
|
||||
if (cfg->flags & CISTPL_CFTABLE_AUDIO)
|
||||
p_dev->config_flags |= CONF_ENABLE_SPKR;
|
||||
|
||||
/* 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 (vcc != cfg->vcc.param[CISTPL_POWER_VNOM]/10000)
|
||||
return -ENODEV;
|
||||
} else if (dflt->vcc.present & (1<<CISTPL_POWER_VNOM)) {
|
||||
if (vcc != dflt->vcc.param[CISTPL_POWER_VNOM]/10000)
|
||||
return -ENODEV;
|
||||
}
|
||||
|
||||
if (cfg->vpp1.present & (1<<CISTPL_POWER_VNOM))
|
||||
p_dev->vpp = cfg->vpp1.param[CISTPL_POWER_VNOM]/10000;
|
||||
else if (dflt->vpp1.present & (1<<CISTPL_POWER_VNOM))
|
||||
p_dev->vpp = dflt->vpp1.param[CISTPL_POWER_VNOM]/10000;
|
||||
|
||||
p_dev->config_flags |= CONF_ENABLE_IRQ;
|
||||
|
||||
/* IO window settings */
|
||||
p_dev->resource[0]->end = p_dev->resource[1]->end = 0;
|
||||
if ((cfg->io.nwin > 0) || (dflt->io.nwin > 0)) {
|
||||
|
@ -223,6 +201,9 @@ static int __devinit sedlbauer_config(struct pcmcia_device *link)
|
|||
|
||||
dev_dbg(&link->dev, "sedlbauer_config(0x%p)\n", link);
|
||||
|
||||
link->config_flags |= CONF_ENABLE_IRQ | CONF_AUTO_CHECK_VCC |
|
||||
CONF_AUTO_SET_VPP | CONF_AUTO_AUDIO;
|
||||
|
||||
/*
|
||||
In this loop, we scan the CIS for configuration table entries,
|
||||
each of which describes a valid card configuration, including
|
||||
|
|
|
@ -145,7 +145,6 @@ static void __devexit teles_detach(struct pcmcia_device *link)
|
|||
static int teles_cs_configcheck(struct pcmcia_device *p_dev,
|
||||
cistpl_cftable_entry_t *cf,
|
||||
cistpl_cftable_entry_t *dflt,
|
||||
unsigned int vcc,
|
||||
void *priv_data)
|
||||
{
|
||||
int j;
|
||||
|
|
|
@ -287,7 +287,6 @@ static int try_io_port(struct pcmcia_device *link)
|
|||
static int axnet_configcheck(struct pcmcia_device *p_dev,
|
||||
cistpl_cftable_entry_t *cfg,
|
||||
cistpl_cftable_entry_t *dflt,
|
||||
unsigned int vcc,
|
||||
void *priv_data)
|
||||
{
|
||||
int i;
|
||||
|
|
|
@ -322,7 +322,6 @@ static int ungermann_try_io_port(struct pcmcia_device *link)
|
|||
static int fmvj18x_ioprobe(struct pcmcia_device *p_dev,
|
||||
cistpl_cftable_entry_t *cfg,
|
||||
cistpl_cftable_entry_t *dflt,
|
||||
unsigned int vcc,
|
||||
void *priv_data)
|
||||
{
|
||||
return 0; /* strange, but that's what the code did already before... */
|
||||
|
|
|
@ -503,7 +503,6 @@ static int try_io_port(struct pcmcia_device *link)
|
|||
static int pcnet_confcheck(struct pcmcia_device *p_dev,
|
||||
cistpl_cftable_entry_t *cfg,
|
||||
cistpl_cftable_entry_t *dflt,
|
||||
unsigned int vcc,
|
||||
void *priv_data)
|
||||
{
|
||||
int *priv = priv_data;
|
||||
|
|
|
@ -420,7 +420,6 @@ static int mhz_3288_power(struct pcmcia_device *link)
|
|||
static int mhz_mfc_config_check(struct pcmcia_device *p_dev,
|
||||
cistpl_cftable_entry_t *cf,
|
||||
cistpl_cftable_entry_t *dflt,
|
||||
unsigned int vcc,
|
||||
void *priv_data)
|
||||
{
|
||||
int k;
|
||||
|
@ -590,7 +589,6 @@ static int mot_setup(struct pcmcia_device *link)
|
|||
static int smc_configcheck(struct pcmcia_device *p_dev,
|
||||
cistpl_cftable_entry_t *cf,
|
||||
cistpl_cftable_entry_t *dflt,
|
||||
unsigned int vcc,
|
||||
void *priv_data)
|
||||
{
|
||||
p_dev->resource[0]->start = cf->io.win[0].base;
|
||||
|
|
|
@ -668,7 +668,6 @@ static int
|
|||
xirc2ps_config_modem(struct pcmcia_device *p_dev,
|
||||
cistpl_cftable_entry_t *cf,
|
||||
cistpl_cftable_entry_t *dflt,
|
||||
unsigned int vcc,
|
||||
void *priv_data)
|
||||
{
|
||||
unsigned int ioaddr;
|
||||
|
@ -688,7 +687,6 @@ static int
|
|||
xirc2ps_config_check(struct pcmcia_device *p_dev,
|
||||
cistpl_cftable_entry_t *cf,
|
||||
cistpl_cftable_entry_t *dflt,
|
||||
unsigned int vcc,
|
||||
void *priv_data)
|
||||
{
|
||||
int *pass = priv_data;
|
||||
|
@ -826,7 +824,8 @@ xirc2ps_config(struct pcmcia_device * link)
|
|||
* the Mako if (on the first pass) the COR bit 5 is set.
|
||||
*/
|
||||
for (pass=0; pass < 2; pass++)
|
||||
if (!pcmcia_loop_config(link, xirc2ps_config_check, &pass))
|
||||
if (!pcmcia_loop_config(link, xirc2ps_config_check,
|
||||
&pass))
|
||||
goto port_found;
|
||||
/* if special option:
|
||||
* try to configure as Ethernet only.
|
||||
|
|
|
@ -140,25 +140,11 @@ static void airo_detach(struct pcmcia_device *link)
|
|||
static int airo_cs_config_check(struct pcmcia_device *p_dev,
|
||||
cistpl_cftable_entry_t *cfg,
|
||||
cistpl_cftable_entry_t *dflt,
|
||||
unsigned int vcc,
|
||||
void *priv_data)
|
||||
{
|
||||
if (cfg->index == 0)
|
||||
return -ENODEV;
|
||||
|
||||
/* Does this card need audio output? */
|
||||
if (cfg->flags & CISTPL_CFTABLE_AUDIO)
|
||||
p_dev->config_flags |= CONF_ENABLE_SPKR;
|
||||
|
||||
/* Use power settings for Vcc and Vpp if present */
|
||||
/* Note that the CIS values need to be rescaled */
|
||||
if (cfg->vpp1.present & (1<<CISTPL_POWER_VNOM))
|
||||
p_dev->vpp = cfg->vpp1.param[CISTPL_POWER_VNOM]/10000;
|
||||
else if (dflt->vpp1.present & (1<<CISTPL_POWER_VNOM))
|
||||
p_dev->vpp = dflt->vpp1.param[CISTPL_POWER_VNOM]/10000;
|
||||
|
||||
p_dev->config_flags |= CONF_ENABLE_IRQ;
|
||||
|
||||
/* IO window settings */
|
||||
p_dev->resource[0]->end = p_dev->resource[1]->end = 0;
|
||||
if ((cfg->io.nwin > 0) || (dflt->io.nwin > 0)) {
|
||||
|
@ -193,6 +179,9 @@ static int airo_config(struct pcmcia_device *link)
|
|||
|
||||
dev_dbg(&link->dev, "airo_config\n");
|
||||
|
||||
link->config_flags |= CONF_ENABLE_IRQ | CONF_AUTO_SET_VPP |
|
||||
CONF_AUTO_AUDIO;
|
||||
|
||||
/*
|
||||
* In this loop, we scan the CIS for configuration table
|
||||
* entries, each of which describes a valid card
|
||||
|
|
|
@ -157,25 +157,11 @@ static int card_present(void *arg)
|
|||
static int atmel_config_check(struct pcmcia_device *p_dev,
|
||||
cistpl_cftable_entry_t *cfg,
|
||||
cistpl_cftable_entry_t *dflt,
|
||||
unsigned int vcc,
|
||||
void *priv_data)
|
||||
{
|
||||
if (cfg->index == 0)
|
||||
return -ENODEV;
|
||||
|
||||
/* Does this card need audio output? */
|
||||
if (cfg->flags & CISTPL_CFTABLE_AUDIO)
|
||||
p_dev->config_flags |= CONF_ENABLE_SPKR;
|
||||
|
||||
/* Use power settings for Vcc and Vpp if present */
|
||||
/* Note that the CIS values need to be rescaled */
|
||||
if (cfg->vpp1.present & (1<<CISTPL_POWER_VNOM))
|
||||
p_dev->vpp = cfg->vpp1.param[CISTPL_POWER_VNOM]/10000;
|
||||
else if (dflt->vpp1.present & (1<<CISTPL_POWER_VNOM))
|
||||
p_dev->vpp = dflt->vpp1.param[CISTPL_POWER_VNOM]/10000;
|
||||
|
||||
p_dev->config_flags |= CONF_ENABLE_IRQ;
|
||||
|
||||
/* IO window settings */
|
||||
p_dev->resource[0]->end = p_dev->resource[1]->end = 0;
|
||||
if ((cfg->io.nwin > 0) || (dflt->io.nwin > 0)) {
|
||||
|
@ -207,6 +193,9 @@ static int atmel_config(struct pcmcia_device *link)
|
|||
|
||||
dev_dbg(&link->dev, "atmel_config\n");
|
||||
|
||||
link->config_flags |= CONF_ENABLE_IRQ | CONF_AUTO_SET_VPP |
|
||||
CONF_AUTO_AUDIO;
|
||||
|
||||
/*
|
||||
In this loop, we scan the CIS for configuration table entries,
|
||||
each of which describes a valid card configuration, including
|
||||
|
|
|
@ -472,7 +472,6 @@ static void prism2_detach(struct pcmcia_device *link)
|
|||
static int prism2_config_check(struct pcmcia_device *p_dev,
|
||||
cistpl_cftable_entry_t *cfg,
|
||||
cistpl_cftable_entry_t *dflt,
|
||||
unsigned int vcc,
|
||||
void *priv_data)
|
||||
{
|
||||
if (cfg->index == 0)
|
||||
|
@ -481,28 +480,6 @@ static int prism2_config_check(struct pcmcia_device *p_dev,
|
|||
PDEBUG(DEBUG_EXTRA, "Checking CFTABLE_ENTRY 0x%02X "
|
||||
"(default 0x%02X)\n", cfg->index, dflt->index);
|
||||
|
||||
/* Does this card need audio output? */
|
||||
if (cfg->flags & CISTPL_CFTABLE_AUDIO)
|
||||
p_dev->config_flags |= CONF_ENABLE_SPKR;
|
||||
|
||||
/* 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 (vcc != cfg->vcc.param[CISTPL_POWER_VNOM] /
|
||||
10000 && !ignore_cis_vcc) {
|
||||
PDEBUG(DEBUG_EXTRA, " Vcc mismatch - skipping"
|
||||
" this entry\n");
|
||||
return -ENODEV;
|
||||
}
|
||||
} else if (dflt->vcc.present & (1 << CISTPL_POWER_VNOM)) {
|
||||
if (vcc != dflt->vcc.param[CISTPL_POWER_VNOM] /
|
||||
10000 && !ignore_cis_vcc) {
|
||||
PDEBUG(DEBUG_EXTRA, " Vcc (default) mismatch "
|
||||
"- skipping this entry\n");
|
||||
return -ENODEV;
|
||||
}
|
||||
}
|
||||
|
||||
if (cfg->vpp1.present & (1 << CISTPL_POWER_VNOM))
|
||||
p_dev->vpp = cfg->vpp1.param[CISTPL_POWER_VNOM] / 10000;
|
||||
else if (dflt->vpp1.present & (1 << CISTPL_POWER_VNOM))
|
||||
|
@ -553,6 +530,10 @@ static int prism2_config(struct pcmcia_device *link)
|
|||
}
|
||||
|
||||
/* Look for an appropriate configuration table entry in the CIS */
|
||||
link->config_flags |= CONF_AUTO_SET_VPP | CONF_AUTO_AUDIO |
|
||||
CONF_AUTO_CHECK_VCC;
|
||||
if (ignore_cis_vcc)
|
||||
link->config_flags &= ~CONF_AUTO_CHECK_VCC;
|
||||
ret = pcmcia_loop_config(link, prism2_config_check, NULL);
|
||||
if (ret) {
|
||||
if (!ignore_cis_vcc)
|
||||
|
|
|
@ -797,7 +797,6 @@ static void if_cs_release(struct pcmcia_device *p_dev)
|
|||
static int if_cs_ioprobe(struct pcmcia_device *p_dev,
|
||||
cistpl_cftable_entry_t *cfg,
|
||||
cistpl_cftable_entry_t *dflt,
|
||||
unsigned int vcc,
|
||||
void *priv_data)
|
||||
{
|
||||
p_dev->resource[0]->flags |= IO_DATA_PATH_WIDTH_AUTO;
|
||||
|
|
|
@ -145,39 +145,11 @@ static void orinoco_cs_detach(struct pcmcia_device *link)
|
|||
static int orinoco_cs_config_check(struct pcmcia_device *p_dev,
|
||||
cistpl_cftable_entry_t *cfg,
|
||||
cistpl_cftable_entry_t *dflt,
|
||||
unsigned int vcc,
|
||||
void *priv_data)
|
||||
{
|
||||
if (cfg->index == 0)
|
||||
goto next_entry;
|
||||
|
||||
/* 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 (vcc != cfg->vcc.param[CISTPL_POWER_VNOM] / 10000) {
|
||||
DEBUG(2, "%s: Vcc mismatch (vcc = %d, CIS = %d)\n",
|
||||
__func__, vcc,
|
||||
cfg->vcc.param[CISTPL_POWER_VNOM] / 10000);
|
||||
if (!ignore_cis_vcc)
|
||||
goto next_entry;
|
||||
}
|
||||
} else if (dflt->vcc.present & (1 << CISTPL_POWER_VNOM)) {
|
||||
if (vcc != dflt->vcc.param[CISTPL_POWER_VNOM] / 10000) {
|
||||
DEBUG(2, "%s: Vcc mismatch (vcc = %d, CIS = %d)\n",
|
||||
__func__, vcc,
|
||||
dflt->vcc.param[CISTPL_POWER_VNOM] / 10000);
|
||||
if (!ignore_cis_vcc)
|
||||
goto next_entry;
|
||||
}
|
||||
}
|
||||
|
||||
if (cfg->vpp1.present & (1 << CISTPL_POWER_VNOM))
|
||||
p_dev->vpp =
|
||||
cfg->vpp1.param[CISTPL_POWER_VNOM] / 10000;
|
||||
else if (dflt->vpp1.present & (1 << CISTPL_POWER_VNOM))
|
||||
p_dev->vpp =
|
||||
dflt->vpp1.param[CISTPL_POWER_VNOM] / 10000;
|
||||
|
||||
/* Do we need to allocate an interrupt? */
|
||||
p_dev->config_flags |= CONF_ENABLE_IRQ;
|
||||
|
||||
|
@ -230,6 +202,9 @@ orinoco_cs_config(struct pcmcia_device *link)
|
|||
* and most client drivers will only use the CIS to fill in
|
||||
* implementation-defined details.
|
||||
*/
|
||||
link->config_flags |= CONF_AUTO_SET_VPP | CONF_AUTO_CHECK_VCC;
|
||||
if (ignore_cis_vcc)
|
||||
link->config_flags &= ~CONF_AUTO_CHECK_VCC;
|
||||
ret = pcmcia_loop_config(link, orinoco_cs_config_check, NULL);
|
||||
if (ret) {
|
||||
if (!ignore_cis_vcc)
|
||||
|
|
|
@ -207,32 +207,11 @@ static void spectrum_cs_detach(struct pcmcia_device *link)
|
|||
static int spectrum_cs_config_check(struct pcmcia_device *p_dev,
|
||||
cistpl_cftable_entry_t *cfg,
|
||||
cistpl_cftable_entry_t *dflt,
|
||||
unsigned int vcc,
|
||||
void *priv_data)
|
||||
{
|
||||
if (cfg->index == 0)
|
||||
goto next_entry;
|
||||
|
||||
/* 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 (vcc != cfg->vcc.param[CISTPL_POWER_VNOM] / 10000) {
|
||||
DEBUG(2, "%s: Vcc mismatch (vcc = %d, CIS = %d)\n",
|
||||
__func__, vcc,
|
||||
cfg->vcc.param[CISTPL_POWER_VNOM] / 10000);
|
||||
if (!ignore_cis_vcc)
|
||||
goto next_entry;
|
||||
}
|
||||
} else if (dflt->vcc.present & (1 << CISTPL_POWER_VNOM)) {
|
||||
if (vcc != dflt->vcc.param[CISTPL_POWER_VNOM] / 10000) {
|
||||
DEBUG(2, "%s: Vcc mismatch (vcc = %d, CIS = %d)\n",
|
||||
__func__, vcc,
|
||||
dflt->vcc.param[CISTPL_POWER_VNOM] / 10000);
|
||||
if (!ignore_cis_vcc)
|
||||
goto next_entry;
|
||||
}
|
||||
}
|
||||
|
||||
if (cfg->vpp1.present & (1 << CISTPL_POWER_VNOM))
|
||||
p_dev->vpp =
|
||||
cfg->vpp1.param[CISTPL_POWER_VNOM] / 10000;
|
||||
|
@ -292,6 +271,9 @@ spectrum_cs_config(struct pcmcia_device *link)
|
|||
* and most client drivers will only use the CIS to fill in
|
||||
* implementation-defined details.
|
||||
*/
|
||||
link->config_flags |= CONF_AUTO_SET_VPP | CONF_AUTO_CHECK_VCC;
|
||||
if (ignore_cis_vcc)
|
||||
link->config_flags &= ~CONF_AUTO_CHECK_VCC;
|
||||
ret = pcmcia_loop_config(link, spectrum_cs_config_check, NULL);
|
||||
if (ret) {
|
||||
if (!ignore_cis_vcc)
|
||||
|
|
|
@ -136,7 +136,6 @@ static void parport_detach(struct pcmcia_device *link)
|
|||
static int parport_config_check(struct pcmcia_device *p_dev,
|
||||
cistpl_cftable_entry_t *cfg,
|
||||
cistpl_cftable_entry_t *dflt,
|
||||
unsigned int vcc,
|
||||
void *priv_data)
|
||||
{
|
||||
if ((cfg->io.nwin > 0) || (dflt->io.nwin > 0)) {
|
||||
|
|
|
@ -131,7 +131,6 @@ struct pcmcia_cfg_mem {
|
|||
int (*conf_check) (struct pcmcia_device *p_dev,
|
||||
cistpl_cftable_entry_t *cfg,
|
||||
cistpl_cftable_entry_t *dflt,
|
||||
unsigned int vcc,
|
||||
void *priv_data);
|
||||
cisparse_t parse;
|
||||
cistpl_cftable_entry_t dflt;
|
||||
|
@ -146,16 +145,46 @@ struct pcmcia_cfg_mem {
|
|||
*/
|
||||
static int pcmcia_do_loop_config(tuple_t *tuple, cisparse_t *parse, void *priv)
|
||||
{
|
||||
cistpl_cftable_entry_t *cfg = &parse->cftable_entry;
|
||||
struct pcmcia_cfg_mem *cfg_mem = priv;
|
||||
struct pcmcia_device *p_dev = cfg_mem->p_dev;
|
||||
cistpl_cftable_entry_t *cfg = &parse->cftable_entry;
|
||||
cistpl_cftable_entry_t *dflt = &cfg_mem->dflt;
|
||||
unsigned int flags = p_dev->config_flags;
|
||||
unsigned int vcc = p_dev->socket->socket.Vcc;
|
||||
|
||||
dev_dbg(&p_dev->dev, "testing configuration %x, autoconf %x\n",
|
||||
cfg->index, flags);
|
||||
|
||||
/* default values */
|
||||
cfg_mem->p_dev->config_index = cfg->index;
|
||||
if (cfg->flags & CISTPL_CFTABLE_DEFAULT)
|
||||
cfg_mem->dflt = *cfg;
|
||||
|
||||
/* check for matching Vcc? */
|
||||
if (flags & CONF_AUTO_CHECK_VCC) {
|
||||
if (cfg->vcc.present & (1 << CISTPL_POWER_VNOM)) {
|
||||
if (vcc != cfg->vcc.param[CISTPL_POWER_VNOM] / 10000)
|
||||
return -ENODEV;
|
||||
} else if (dflt->vcc.present & (1 << CISTPL_POWER_VNOM)) {
|
||||
if (vcc != dflt->vcc.param[CISTPL_POWER_VNOM] / 10000)
|
||||
return -ENODEV;
|
||||
}
|
||||
}
|
||||
|
||||
/* set Vpp? */
|
||||
if (flags & CONF_AUTO_SET_VPP) {
|
||||
if (cfg->vpp1.present & (1 << CISTPL_POWER_VNOM))
|
||||
p_dev->vpp = cfg->vpp1.param[CISTPL_POWER_VNOM] / 10000;
|
||||
else if (dflt->vpp1.present & (1 << CISTPL_POWER_VNOM))
|
||||
p_dev->vpp =
|
||||
dflt->vpp1.param[CISTPL_POWER_VNOM] / 10000;
|
||||
}
|
||||
|
||||
/* enable audio? */
|
||||
if ((flags & CONF_AUTO_AUDIO) && (cfg->flags & CISTPL_CFTABLE_AUDIO))
|
||||
p_dev->config_flags |= CONF_ENABLE_SPKR;
|
||||
|
||||
return cfg_mem->conf_check(cfg_mem->p_dev, cfg, &cfg_mem->dflt,
|
||||
cfg_mem->p_dev->socket->socket.Vcc,
|
||||
cfg_mem->priv_data);
|
||||
}
|
||||
|
||||
|
@ -176,7 +205,6 @@ int pcmcia_loop_config(struct pcmcia_device *p_dev,
|
|||
int (*conf_check) (struct pcmcia_device *p_dev,
|
||||
cistpl_cftable_entry_t *cfg,
|
||||
cistpl_cftable_entry_t *dflt,
|
||||
unsigned int vcc,
|
||||
void *priv_data),
|
||||
void *priv_data)
|
||||
{
|
||||
|
|
|
@ -124,7 +124,6 @@ static void aha152x_detach(struct pcmcia_device *link)
|
|||
static int aha152x_config_check(struct pcmcia_device *p_dev,
|
||||
cistpl_cftable_entry_t *cfg,
|
||||
cistpl_cftable_entry_t *dflt,
|
||||
unsigned int vcc,
|
||||
void *priv_data)
|
||||
{
|
||||
p_dev->io_lines = 10;
|
||||
|
|
|
@ -106,7 +106,6 @@ static void fdomain_detach(struct pcmcia_device *link)
|
|||
static int fdomain_config_check(struct pcmcia_device *p_dev,
|
||||
cistpl_cftable_entry_t *cfg,
|
||||
cistpl_cftable_entry_t *dflt,
|
||||
unsigned int vcc,
|
||||
void *priv_data)
|
||||
{
|
||||
p_dev->io_lines = 10;
|
||||
|
|
|
@ -1597,7 +1597,6 @@ static void nsp_cs_detach(struct pcmcia_device *link)
|
|||
static int nsp_cs_config_check(struct pcmcia_device *p_dev,
|
||||
cistpl_cftable_entry_t *cfg,
|
||||
cistpl_cftable_entry_t *dflt,
|
||||
unsigned int vcc,
|
||||
void *priv_data)
|
||||
{
|
||||
nsp_hw_data *data = priv_data;
|
||||
|
@ -1605,78 +1604,50 @@ static int nsp_cs_config_check(struct pcmcia_device *p_dev,
|
|||
if (cfg->index == 0)
|
||||
return -ENODEV;
|
||||
|
||||
/* Does this card need audio output? */
|
||||
if (cfg->flags & CISTPL_CFTABLE_AUDIO)
|
||||
p_dev->config_flags |= CONF_ENABLE_SPKR;
|
||||
|
||||
/* 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 (vcc != cfg->vcc.param[CISTPL_POWER_VNOM]/10000)
|
||||
return -ENODEV;
|
||||
else if (dflt->vcc.present & (1<<CISTPL_POWER_VNOM)) {
|
||||
if (vcc != dflt->vcc.param[CISTPL_POWER_VNOM]/10000)
|
||||
return -ENODEV;
|
||||
/* IO window settings */
|
||||
p_dev->resource[0]->end = p_dev->resource[1]->end = 0;
|
||||
if ((cfg->io.nwin > 0) || (dflt->io.nwin > 0)) {
|
||||
cistpl_io_t *io = (cfg->io.nwin) ? &cfg->io : &dflt->io;
|
||||
p_dev->io_lines = io->flags & CISTPL_IO_LINES_MASK;
|
||||
p_dev->resource[0]->flags &= ~IO_DATA_PATH_WIDTH;
|
||||
p_dev->resource[0]->flags |=
|
||||
pcmcia_io_cfg_data_width(io->flags);
|
||||
p_dev->resource[0]->start = io->win[0].base;
|
||||
p_dev->resource[0]->end = io->win[0].len;
|
||||
if (io->nwin > 1) {
|
||||
p_dev->resource[1]->flags = p_dev->resource[0]->flags;
|
||||
p_dev->resource[1]->start = io->win[1].base;
|
||||
p_dev->resource[1]->end = io->win[1].len;
|
||||
}
|
||||
|
||||
if (cfg->vpp1.present & (1 << CISTPL_POWER_VNOM)) {
|
||||
p_dev->vpp =
|
||||
cfg->vpp1.param[CISTPL_POWER_VNOM] / 10000;
|
||||
} else if (dflt->vpp1.present & (1 << CISTPL_POWER_VNOM)) {
|
||||
p_dev->vpp =
|
||||
dflt->vpp1.param[CISTPL_POWER_VNOM] / 10000;
|
||||
}
|
||||
|
||||
/* Do we need to allocate an interrupt? */
|
||||
p_dev->config_flags |= CONF_ENABLE_IRQ;
|
||||
|
||||
/* IO window settings */
|
||||
p_dev->resource[0]->end = p_dev->resource[1]->end = 0;
|
||||
if ((cfg->io.nwin > 0) || (dflt->io.nwin > 0)) {
|
||||
cistpl_io_t *io = (cfg->io.nwin) ? &cfg->io : &dflt->io;
|
||||
p_dev->io_lines = io->flags & CISTPL_IO_LINES_MASK;
|
||||
p_dev->resource[0]->flags &= ~IO_DATA_PATH_WIDTH;
|
||||
p_dev->resource[0]->flags |=
|
||||
pcmcia_io_cfg_data_width(io->flags);
|
||||
p_dev->resource[0]->start = io->win[0].base;
|
||||
p_dev->resource[0]->end = io->win[0].len;
|
||||
if (io->nwin > 1) {
|
||||
p_dev->resource[1]->flags =
|
||||
p_dev->resource[0]->flags;
|
||||
p_dev->resource[1]->start = io->win[1].base;
|
||||
p_dev->resource[1]->end = io->win[1].len;
|
||||
}
|
||||
/* This reserves IO space but doesn't actually enable it */
|
||||
if (pcmcia_request_io(p_dev) != 0)
|
||||
goto next_entry;
|
||||
}
|
||||
|
||||
if ((cfg->mem.nwin > 0) || (dflt->mem.nwin > 0)) {
|
||||
cistpl_mem_t *mem =
|
||||
(cfg->mem.nwin) ? &cfg->mem : &dflt->mem;
|
||||
p_dev->resource[2]->flags |= (WIN_DATA_WIDTH_16 |
|
||||
WIN_MEMORY_TYPE_CM |
|
||||
WIN_ENABLE);
|
||||
p_dev->resource[2]->start = mem->win[0].host_addr;
|
||||
p_dev->resource[2]->end = mem->win[0].len;
|
||||
if (p_dev->resource[2]->end < 0x1000)
|
||||
p_dev->resource[2]->end = 0x1000;
|
||||
if (pcmcia_request_window(p_dev, p_dev->resource[2],
|
||||
0) != 0)
|
||||
goto next_entry;
|
||||
if (pcmcia_map_mem_page(p_dev, p_dev->resource[2],
|
||||
mem->win[0].card_addr) != 0)
|
||||
goto next_entry;
|
||||
|
||||
data->MmioAddress = (unsigned long)
|
||||
ioremap_nocache(p_dev->resource[2]->start,
|
||||
resource_size(p_dev->resource[2]));
|
||||
data->MmioLength = resource_size(p_dev->resource[2]);
|
||||
}
|
||||
/* If we got this far, we're cool! */
|
||||
return 0;
|
||||
/* This reserves IO space but doesn't actually enable it */
|
||||
if (pcmcia_request_io(p_dev) != 0)
|
||||
goto next_entry;
|
||||
}
|
||||
|
||||
if ((cfg->mem.nwin > 0) || (dflt->mem.nwin > 0)) {
|
||||
cistpl_mem_t *mem =
|
||||
(cfg->mem.nwin) ? &cfg->mem : &dflt->mem;
|
||||
p_dev->resource[2]->flags |= (WIN_DATA_WIDTH_16 |
|
||||
WIN_MEMORY_TYPE_CM |
|
||||
WIN_ENABLE);
|
||||
p_dev->resource[2]->start = mem->win[0].host_addr;
|
||||
p_dev->resource[2]->end = mem->win[0].len;
|
||||
if (p_dev->resource[2]->end < 0x1000)
|
||||
p_dev->resource[2]->end = 0x1000;
|
||||
if (pcmcia_request_window(p_dev, p_dev->resource[2], 0) != 0)
|
||||
goto next_entry;
|
||||
if (pcmcia_map_mem_page(p_dev, p_dev->resource[2],
|
||||
mem->win[0].card_addr) != 0)
|
||||
goto next_entry;
|
||||
|
||||
data->MmioAddress = (unsigned long)
|
||||
ioremap_nocache(p_dev->resource[2]->start,
|
||||
resource_size(p_dev->resource[2]));
|
||||
data->MmioLength = resource_size(p_dev->resource[2]);
|
||||
}
|
||||
/* If we got this far, we're cool! */
|
||||
return 0;
|
||||
|
||||
next_entry:
|
||||
nsp_dbg(NSP_DEBUG_INIT, "next");
|
||||
pcmcia_disable_device(p_dev);
|
||||
|
@ -1692,6 +1663,9 @@ static int nsp_cs_config(struct pcmcia_device *link)
|
|||
|
||||
nsp_dbg(NSP_DEBUG_INIT, "in");
|
||||
|
||||
link->config_flags |= CONF_ENABLE_IRQ | CONF_AUTO_CHECK_VCC |
|
||||
CONF_AUTO_SET_VPP | CONF_AUTO_AUDIO;
|
||||
|
||||
ret = pcmcia_loop_config(link, nsp_cs_config_check, data);
|
||||
if (ret)
|
||||
goto cs_failed;
|
||||
|
|
|
@ -179,7 +179,6 @@ static void qlogic_detach(struct pcmcia_device *link)
|
|||
static int qlogic_config_check(struct pcmcia_device *p_dev,
|
||||
cistpl_cftable_entry_t *cfg,
|
||||
cistpl_cftable_entry_t *dflt,
|
||||
unsigned int vcc,
|
||||
void *priv_data)
|
||||
{
|
||||
p_dev->io_lines = 10;
|
||||
|
|
|
@ -686,7 +686,6 @@ static struct scsi_host_template sym53c500_driver_template = {
|
|||
static int SYM53C500_config_check(struct pcmcia_device *p_dev,
|
||||
cistpl_cftable_entry_t *cfg,
|
||||
cistpl_cftable_entry_t *dflt,
|
||||
unsigned int vcc,
|
||||
void *priv_data)
|
||||
{
|
||||
p_dev->io_lines = 10;
|
||||
|
|
|
@ -427,16 +427,11 @@ static int pfc_config(struct pcmcia_device *p_dev)
|
|||
static int simple_config_check(struct pcmcia_device *p_dev,
|
||||
cistpl_cftable_entry_t *cf,
|
||||
cistpl_cftable_entry_t *dflt,
|
||||
unsigned int vcc,
|
||||
void *priv_data)
|
||||
{
|
||||
static const int size_table[2] = { 8, 16 };
|
||||
int *try = priv_data;
|
||||
|
||||
if (cf->vpp1.present & (1 << CISTPL_POWER_VNOM))
|
||||
p_dev->vpp =
|
||||
cf->vpp1.param[CISTPL_POWER_VNOM] / 10000;
|
||||
|
||||
p_dev->io_lines = ((*try & 0x1) == 0) ?
|
||||
16 : cf->io.flags & CISTPL_IO_LINES_MASK;
|
||||
|
||||
|
@ -452,7 +447,6 @@ static int simple_config_check(struct pcmcia_device *p_dev,
|
|||
static int simple_config_check_notpicky(struct pcmcia_device *p_dev,
|
||||
cistpl_cftable_entry_t *cf,
|
||||
cistpl_cftable_entry_t *dflt,
|
||||
unsigned int vcc,
|
||||
void *priv_data)
|
||||
{
|
||||
static const unsigned int base[5] = { 0x3f8, 0x2f8, 0x3e8, 0x2e8, 0x0 };
|
||||
|
@ -479,6 +473,7 @@ static int simple_config(struct pcmcia_device *link)
|
|||
|
||||
/* First pass: look for a config entry that looks normal.
|
||||
* Two tries: without IO aliases, then with aliases */
|
||||
link->config_flags |= CONF_AUTO_SET_VPP;
|
||||
for (try = 0; try < 4; try++)
|
||||
if (!pcmcia_loop_config(link, simple_config_check, &try))
|
||||
goto found_port;
|
||||
|
@ -511,7 +506,6 @@ found_port:
|
|||
static int multi_config_check(struct pcmcia_device *p_dev,
|
||||
cistpl_cftable_entry_t *cf,
|
||||
cistpl_cftable_entry_t *dflt,
|
||||
unsigned int vcc,
|
||||
void *priv_data)
|
||||
{
|
||||
int *base2 = priv_data;
|
||||
|
@ -532,7 +526,6 @@ static int multi_config_check(struct pcmcia_device *p_dev,
|
|||
static int multi_config_check_notpicky(struct pcmcia_device *p_dev,
|
||||
cistpl_cftable_entry_t *cf,
|
||||
cistpl_cftable_entry_t *dflt,
|
||||
unsigned int vcc,
|
||||
void *priv_data)
|
||||
{
|
||||
int *base2 = priv_data;
|
||||
|
@ -621,7 +614,6 @@ static int multi_config(struct pcmcia_device *link)
|
|||
static int serial_check_for_multi(struct pcmcia_device *p_dev,
|
||||
cistpl_cftable_entry_t *cf,
|
||||
cistpl_cftable_entry_t *dflt,
|
||||
unsigned int vcc,
|
||||
void *priv_data)
|
||||
{
|
||||
struct serial_info *info = p_dev->priv;
|
||||
|
|
|
@ -712,7 +712,6 @@ static void das16cs_pcmcia_detach(struct pcmcia_device *link)
|
|||
static int das16cs_pcmcia_config_loop(struct pcmcia_device *p_dev,
|
||||
cistpl_cftable_entry_t *cfg,
|
||||
cistpl_cftable_entry_t *dflt,
|
||||
unsigned int vcc,
|
||||
void *priv_data)
|
||||
{
|
||||
if (cfg->index == 0)
|
||||
|
|
|
@ -194,7 +194,6 @@ static void das08_pcmcia_detach(struct pcmcia_device *link)
|
|||
static int das08_pcmcia_config_loop(struct pcmcia_device *p_dev,
|
||||
cistpl_cftable_entry_t *cfg,
|
||||
cistpl_cftable_entry_t *dflt,
|
||||
unsigned int vcc,
|
||||
void *priv_data)
|
||||
{
|
||||
if (cfg->index == 0)
|
||||
|
|
|
@ -532,19 +532,11 @@ static void dio700_cs_detach(struct pcmcia_device *link)
|
|||
static int dio700_pcmcia_config_loop(struct pcmcia_device *p_dev,
|
||||
cistpl_cftable_entry_t *cfg,
|
||||
cistpl_cftable_entry_t *dflt,
|
||||
unsigned int vcc,
|
||||
void *priv_data)
|
||||
{
|
||||
if (cfg->index == 0)
|
||||
return -ENODEV;
|
||||
|
||||
/* Does this card need audio output? */
|
||||
if (cfg->flags & CISTPL_CFTABLE_AUDIO)
|
||||
p_dev->config_flags |= CONF_ENABLE_SPKR;
|
||||
|
||||
/* Do we need to allocate an interrupt? */
|
||||
p_dev->config_flags |= CONF_ENABLE_IRQ;
|
||||
|
||||
/* IO window settings */
|
||||
p_dev->resource[0]->end = p_dev->resource[1]->end = 0;
|
||||
if ((cfg->io.nwin > 0) || (dflt->io.nwin > 0)) {
|
||||
|
@ -578,6 +570,8 @@ static void dio700_config(struct pcmcia_device *link)
|
|||
|
||||
dev_dbg(&link->dev, "dio700_config\n");
|
||||
|
||||
link->config_flags |= CONF_ENABLE_IRQ | CONF_AUTO_AUDIO;
|
||||
|
||||
ret = pcmcia_loop_config(link, dio700_pcmcia_config_loop, NULL);
|
||||
if (ret) {
|
||||
dev_warn(&link->dev, "no configuration found\n");
|
||||
|
|
|
@ -284,19 +284,11 @@ static void dio24_cs_detach(struct pcmcia_device *link)
|
|||
static int dio24_pcmcia_config_loop(struct pcmcia_device *p_dev,
|
||||
cistpl_cftable_entry_t *cfg,
|
||||
cistpl_cftable_entry_t *dflt,
|
||||
unsigned int vcc,
|
||||
void *priv_data)
|
||||
{
|
||||
if (cfg->index == 0)
|
||||
return -ENODEV;
|
||||
|
||||
/* Does this card need audio output? */
|
||||
if (cfg->flags & CISTPL_CFTABLE_AUDIO)
|
||||
p_dev->config_flags |= CONF_ENABLE_SPKR;
|
||||
|
||||
/* Do we need to allocate an interrupt? */
|
||||
p_dev->config_flags |= CONF_ENABLE_IRQ;
|
||||
|
||||
/* IO window settings */
|
||||
p_dev->resource[0]->end = p_dev->resource[1]->end = 0;
|
||||
if ((cfg->io.nwin > 0) || (dflt->io.nwin > 0)) {
|
||||
|
@ -329,6 +321,8 @@ static void dio24_config(struct pcmcia_device *link)
|
|||
|
||||
dev_dbg(&link->dev, "dio24_config\n");
|
||||
|
||||
link->config_flags |= CONF_ENABLE_IRQ | CONF_AUTO_AUDIO;
|
||||
|
||||
ret = pcmcia_loop_config(link, dio24_pcmcia_config_loop, NULL);
|
||||
if (ret) {
|
||||
dev_warn(&link->dev, "no configuration found\n");
|
||||
|
|
|
@ -263,19 +263,11 @@ static void labpc_cs_detach(struct pcmcia_device *link)
|
|||
static int labpc_pcmcia_config_loop(struct pcmcia_device *p_dev,
|
||||
cistpl_cftable_entry_t *cfg,
|
||||
cistpl_cftable_entry_t *dflt,
|
||||
unsigned int vcc,
|
||||
void *priv_data)
|
||||
{
|
||||
if (cfg->index == 0)
|
||||
return -ENODEV;
|
||||
|
||||
/* Does this card need audio output? */
|
||||
if (cfg->flags & CISTPL_CFTABLE_AUDIO)
|
||||
p_dev->config_flags |= CONF_ENABLE_SPKR;
|
||||
|
||||
/* Do we need to allocate an interrupt? */
|
||||
p_dev->config_flags |= CONF_ENABLE_IRQ | CONF_ENABLE_PULSE_IRQ;
|
||||
|
||||
/* IO window settings */
|
||||
p_dev->resource[0]->end = p_dev->resource[1]->end = 0;
|
||||
if ((cfg->io.nwin > 0) || (dflt->io.nwin > 0)) {
|
||||
|
@ -307,6 +299,9 @@ static void labpc_config(struct pcmcia_device *link)
|
|||
|
||||
dev_dbg(&link->dev, "labpc_config\n");
|
||||
|
||||
link->config_flags |= CONF_ENABLE_IRQ | CONF_ENABLE_PULSE_IRQ |
|
||||
CONF_AUTO_AUDIO;
|
||||
|
||||
ret = pcmcia_loop_config(link, labpc_pcmcia_config_loop, NULL);
|
||||
if (ret) {
|
||||
dev_warn(&link->dev, "no configuration found\n");
|
||||
|
|
|
@ -302,7 +302,6 @@ static int mio_cs_resume(struct pcmcia_device *link)
|
|||
static int mio_pcmcia_config_loop(struct pcmcia_device *p_dev,
|
||||
cistpl_cftable_entry_t *cfg,
|
||||
cistpl_cftable_entry_t *dflt,
|
||||
unsigned int vcc,
|
||||
void *priv_data)
|
||||
{
|
||||
int base, ret;
|
||||
|
|
|
@ -1071,7 +1071,6 @@ static void daqp_cs_detach(struct pcmcia_device *link)
|
|||
static int daqp_pcmcia_config_loop(struct pcmcia_device *p_dev,
|
||||
cistpl_cftable_entry_t *cfg,
|
||||
cistpl_cftable_entry_t *dflt,
|
||||
unsigned int vcc,
|
||||
void *priv_data)
|
||||
{
|
||||
if (cfg->index == 0)
|
||||
|
|
|
@ -112,7 +112,6 @@ failed:
|
|||
static int ixj_config_check(struct pcmcia_device *p_dev,
|
||||
cistpl_cftable_entry_t *cfg,
|
||||
cistpl_cftable_entry_t *dflt,
|
||||
unsigned int vcc,
|
||||
void *priv_data)
|
||||
{
|
||||
if ((cfg->io.nwin > 0) || (dflt->io.nwin > 0)) {
|
||||
|
|
|
@ -134,32 +134,11 @@ static void sl811_cs_release(struct pcmcia_device * link)
|
|||
static int sl811_cs_config_check(struct pcmcia_device *p_dev,
|
||||
cistpl_cftable_entry_t *cfg,
|
||||
cistpl_cftable_entry_t *dflt,
|
||||
unsigned int vcc,
|
||||
void *priv_data)
|
||||
{
|
||||
if (cfg->index == 0)
|
||||
return -ENODEV;
|
||||
|
||||
/* 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 (cfg->vcc.param[CISTPL_POWER_VNOM]/10000 != vcc)
|
||||
return -ENODEV;
|
||||
} else if (dflt->vcc.present & (1<<CISTPL_POWER_VNOM)) {
|
||||
if (dflt->vcc.param[CISTPL_POWER_VNOM]/10000 != vcc)
|
||||
return -ENODEV;
|
||||
}
|
||||
|
||||
if (cfg->vpp1.present & (1<<CISTPL_POWER_VNOM))
|
||||
p_dev->vpp =
|
||||
cfg->vpp1.param[CISTPL_POWER_VNOM]/10000;
|
||||
else if (dflt->vpp1.present & (1<<CISTPL_POWER_VNOM))
|
||||
p_dev->vpp =
|
||||
dflt->vpp1.param[CISTPL_POWER_VNOM]/10000;
|
||||
|
||||
/* we need an interrupt */
|
||||
p_dev->config_flags |= CONF_ENABLE_IRQ;
|
||||
|
||||
/* IO window settings */
|
||||
p_dev->resource[0]->end = p_dev->resource[1]->end = 0;
|
||||
if ((cfg->io.nwin > 0) || (dflt->io.nwin > 0)) {
|
||||
|
@ -184,6 +163,9 @@ static int sl811_cs_config(struct pcmcia_device *link)
|
|||
|
||||
dev_dbg(&link->dev, "sl811_cs_config\n");
|
||||
|
||||
link->config_flags |= CONF_ENABLE_IRQ | CONF_AUTO_SET_VPP |
|
||||
CONF_AUTO_CHECK_VCC;
|
||||
|
||||
if (pcmcia_loop_config(link, sl811_cs_config_check, NULL))
|
||||
goto failed;
|
||||
|
||||
|
|
|
@ -177,7 +177,6 @@ int pcmcia_loop_config(struct pcmcia_device *p_dev,
|
|||
int (*conf_check) (struct pcmcia_device *p_dev,
|
||||
cistpl_cftable_entry_t *cf,
|
||||
cistpl_cftable_entry_t *dflt,
|
||||
unsigned int vcc,
|
||||
void *priv_data),
|
||||
void *priv_data);
|
||||
|
||||
|
@ -270,6 +269,12 @@ static inline int pcmcia_io_cfg_data_width(unsigned int flags)
|
|||
#define CONF_ENABLE_PULSE_IRQ 0x04
|
||||
#define CONF_ENABLE_ESR 0x08
|
||||
|
||||
/* flags used by pcmcia_loop_config() autoconfiguration */
|
||||
#define CONF_AUTO_CHECK_VCC 0x10 /* check for matching Vcc? */
|
||||
#define CONF_AUTO_SET_VPP 0x20 /* set Vpp? */
|
||||
#define CONF_AUTO_AUDIO 0x40 /* enable audio line? */
|
||||
|
||||
|
||||
#endif /* __KERNEL__ */
|
||||
|
||||
#endif /* _LINUX_DS_H */
|
||||
|
|
Loading…
Reference in a new issue