diff options
44 files changed, 515 insertions, 1025 deletions
diff --git a/Documentation/pcmcia/driver-changes.txt b/Documentation/pcmcia/driver-changes.txt index 62a029f24f46..dd04361dd361 100644 --- a/Documentation/pcmcia/driver-changes.txt +++ b/Documentation/pcmcia/driver-changes.txt | |||
| @@ -1,4 +1,16 @@ | |||
| 1 | This file details changes in 2.6 which affect PCMCIA card driver authors: | 1 | This file details changes in 2.6 which affect PCMCIA card driver authors: |
| 2 | * pcmcia_loop_config() and autoconfiguration (as of 2.6.36) | ||
| 3 | If struct pcmcia_device *p_dev->config_flags is set accordingly, | ||
| 4 | pcmcia_loop_config() now sets up certain configuration values | ||
| 5 | automatically, though the driver may still override the settings | ||
| 6 | in the callback function. The following autoconfiguration options | ||
| 7 | are provided at the moment: | ||
| 8 | CONF_AUTO_CHECK_VCC : check for matching Vcc | ||
| 9 | CONF_AUTO_SET_VPP : set Vpp | ||
| 10 | CONF_AUTO_AUDIO : auto-enable audio line, if required | ||
| 11 | CONF_AUTO_SET_IO : set ioport resources (->resource[0,1]) | ||
| 12 | CONF_AUTO_SET_IOMEM : set first iomem resource (->resource[2]) | ||
| 13 | |||
| 2 | * pcmcia_request_configuration -> pcmcia_enable_device (as of 2.6.36) | 14 | * pcmcia_request_configuration -> pcmcia_enable_device (as of 2.6.36) |
| 3 | pcmcia_request_configuration() got renamed to pcmcia_enable_device(), | 15 | pcmcia_request_configuration() got renamed to pcmcia_enable_device(), |
| 4 | as it mirrors pcmcia_disable_device(). Configuration settings are now | 16 | as it mirrors pcmcia_disable_device(). Configuration settings are now |
diff --git a/drivers/ata/pata_pcmcia.c b/drivers/ata/pata_pcmcia.c index 954f43c512f1..88cb03c36963 100644 --- a/drivers/ata/pata_pcmcia.c +++ b/drivers/ata/pata_pcmcia.c | |||
| @@ -167,45 +167,26 @@ static struct ata_port_operations pcmcia_8bit_port_ops = { | |||
| 167 | }; | 167 | }; |
| 168 | 168 | ||
| 169 | 169 | ||
| 170 | struct pcmcia_config_check { | 170 | static int pcmcia_check_one_config(struct pcmcia_device *pdev, void *priv_data) |
| 171 | unsigned long ctl_base; | ||
| 172 | int is_kme; | ||
| 173 | }; | ||
| 174 | |||
| 175 | static int pcmcia_check_one_config(struct pcmcia_device *pdev, | ||
| 176 | cistpl_cftable_entry_t *cfg, | ||
| 177 | cistpl_cftable_entry_t *dflt, | ||
| 178 | void *priv_data) | ||
| 179 | { | 171 | { |
| 180 | struct pcmcia_config_check *stk = priv_data; | 172 | int *is_kme = priv_data; |
| 181 | 173 | ||
| 182 | if ((cfg->io.nwin > 0) || (dflt->io.nwin > 0)) { | 174 | if (!(pdev->resource[0]->flags & IO_DATA_PATH_WIDTH_8)) { |
| 183 | cistpl_io_t *io = (cfg->io.nwin) ? &cfg->io : &dflt->io; | 175 | pdev->resource[0]->flags &= ~IO_DATA_PATH_WIDTH; |
| 184 | pdev->io_lines = io->flags & CISTPL_IO_LINES_MASK; | 176 | pdev->resource[0]->flags |= IO_DATA_PATH_WIDTH_AUTO; |
| 185 | pdev->resource[0]->start = io->win[0].base; | 177 | } |
| 186 | if (!(io->flags & CISTPL_IO_16BIT)) { | 178 | pdev->resource[1]->flags &= ~IO_DATA_PATH_WIDTH; |
| 187 | pdev->resource[0]->flags &= ~IO_DATA_PATH_WIDTH; | 179 | pdev->resource[1]->flags |= IO_DATA_PATH_WIDTH_8; |
| 188 | pdev->resource[0]->flags |= IO_DATA_PATH_WIDTH_8; | 180 | |
| 189 | } | 181 | if (pdev->resource[1]->end) { |
| 190 | if (io->nwin == 2) { | 182 | pdev->resource[0]->end = 8; |
| 191 | pdev->resource[0]->end = 8; | 183 | pdev->resource[1]->end = (*is_kme) ? 2 : 1; |
| 192 | pdev->resource[1]->start = io->win[1].base; | 184 | } else { |
| 193 | pdev->resource[1]->end = (stk->is_kme) ? 2 : 1; | 185 | if (pdev->resource[0]->end < 16) |
| 194 | if (pcmcia_request_io(pdev) != 0) | ||
| 195 | return -ENODEV; | ||
| 196 | stk->ctl_base = pdev->resource[1]->start; | ||
| 197 | } else if ((io->nwin == 1) && (io->win[0].len >= 16)) { | ||
| 198 | pdev->resource[0]->end = io->win[0].len; | ||
| 199 | pdev->resource[1]->end = 0; | ||
| 200 | if (pcmcia_request_io(pdev) != 0) | ||
| 201 | return -ENODEV; | ||
| 202 | stk->ctl_base = pdev->resource[0]->start + 0x0e; | ||
| 203 | } else | ||
| 204 | return -ENODEV; | 186 | return -ENODEV; |
| 205 | /* If we've got this far, we're done */ | ||
| 206 | return 0; | ||
| 207 | } | 187 | } |
| 208 | return -ENODEV; | 188 | |
| 189 | return pcmcia_request_io(pdev); | ||
| 209 | } | 190 | } |
| 210 | 191 | ||
| 211 | /** | 192 | /** |
| @@ -220,7 +201,6 @@ static int pcmcia_init_one(struct pcmcia_device *pdev) | |||
| 220 | { | 201 | { |
| 221 | struct ata_host *host; | 202 | struct ata_host *host; |
| 222 | struct ata_port *ap; | 203 | struct ata_port *ap; |
| 223 | struct pcmcia_config_check *stk = NULL; | ||
| 224 | int is_kme = 0, ret = -ENOMEM, p; | 204 | int is_kme = 0, ret = -ENOMEM, p; |
| 225 | unsigned long io_base, ctl_base; | 205 | unsigned long io_base, ctl_base; |
| 226 | void __iomem *io_addr, *ctl_addr; | 206 | void __iomem *io_addr, *ctl_addr; |
| @@ -228,10 +208,8 @@ static int pcmcia_init_one(struct pcmcia_device *pdev) | |||
| 228 | struct ata_port_operations *ops = &pcmcia_port_ops; | 208 | struct ata_port_operations *ops = &pcmcia_port_ops; |
| 229 | 209 | ||
| 230 | /* Set up attributes in order to probe card and get resources */ | 210 | /* Set up attributes in order to probe card and get resources */ |
| 231 | pdev->resource[0]->flags |= IO_DATA_PATH_WIDTH_AUTO; | 211 | pdev->config_flags |= CONF_ENABLE_IRQ | CONF_AUTO_SET_IO | |
| 232 | pdev->resource[1]->flags |= IO_DATA_PATH_WIDTH_8; | 212 | CONF_AUTO_SET_VPP | CONF_AUTO_CHECK_VCC; |
| 233 | pdev->config_flags |= CONF_ENABLE_IRQ; | ||
| 234 | pdev->config_flags |= CONF_AUTO_SET_VPP | CONF_AUTO_CHECK_VCC; | ||
| 235 | 213 | ||
| 236 | /* See if we have a manufacturer identifier. Use it to set is_kme for | 214 | /* See if we have a manufacturer identifier. Use it to set is_kme for |
| 237 | vendor quirks */ | 215 | vendor quirks */ |
| @@ -239,21 +217,17 @@ static int pcmcia_init_one(struct pcmcia_device *pdev) | |||
| 239 | ((pdev->card_id == PRODID_KME_KXLC005_A) || | 217 | ((pdev->card_id == PRODID_KME_KXLC005_A) || |
| 240 | (pdev->card_id == PRODID_KME_KXLC005_B))); | 218 | (pdev->card_id == PRODID_KME_KXLC005_B))); |
| 241 | 219 | ||
| 242 | /* Allocate resoure probing structures */ | 220 | if (pcmcia_loop_config(pdev, pcmcia_check_one_config, &is_kme)) { |
| 243 | |||
| 244 | stk = kzalloc(sizeof(*stk), GFP_KERNEL); | ||
| 245 | if (!stk) | ||
| 246 | goto out1; | ||
| 247 | stk->is_kme = is_kme; | ||
| 248 | io_base = ctl_base = 0; | ||
| 249 | |||
| 250 | if (pcmcia_loop_config(pdev, pcmcia_check_one_config, stk)) { | ||
| 251 | pdev->config_flags &= ~CONF_AUTO_CHECK_VCC; | 221 | pdev->config_flags &= ~CONF_AUTO_CHECK_VCC; |
| 252 | if (pcmcia_loop_config(pdev, pcmcia_check_one_config, stk)) | 222 | if (pcmcia_loop_config(pdev, pcmcia_check_one_config, &is_kme)) |
| 253 | goto failed; /* No suitable config found */ | 223 | goto failed; /* No suitable config found */ |
| 254 | } | 224 | } |
| 255 | io_base = pdev->resource[0]->start; | 225 | io_base = pdev->resource[0]->start; |
| 256 | ctl_base = stk->ctl_base; | 226 | if (pdev->resource[1]->end) |
| 227 | ctl_base = pdev->resource[1]->start; | ||
| 228 | else | ||
| 229 | ctl_base = pdev->resource[0]->start + 0x0e; | ||
| 230 | |||
| 257 | if (!pdev->irq) | 231 | if (!pdev->irq) |
| 258 | goto failed; | 232 | goto failed; |
| 259 | 233 | ||
| @@ -310,13 +284,10 @@ static int pcmcia_init_one(struct pcmcia_device *pdev) | |||
| 310 | goto failed; | 284 | goto failed; |
| 311 | 285 | ||
| 312 | pdev->priv = host; | 286 | pdev->priv = host; |
| 313 | kfree(stk); | ||
| 314 | return 0; | 287 | return 0; |
| 315 | 288 | ||
| 316 | failed: | 289 | failed: |
| 317 | kfree(stk); | ||
| 318 | pcmcia_disable_device(pdev); | 290 | pcmcia_disable_device(pdev); |
| 319 | out1: | ||
| 320 | return ret; | 291 | return ret; |
| 321 | } | 292 | } |
| 322 | 293 | ||
diff --git a/drivers/bluetooth/bt3c_cs.c b/drivers/bluetooth/bt3c_cs.c index 97338a3aae1a..8b8be35fe312 100644 --- a/drivers/bluetooth/bt3c_cs.c +++ b/drivers/bluetooth/bt3c_cs.c | |||
| @@ -656,10 +656,8 @@ static int bt3c_probe(struct pcmcia_device *link) | |||
| 656 | info->p_dev = link; | 656 | info->p_dev = link; |
| 657 | link->priv = info; | 657 | link->priv = info; |
| 658 | 658 | ||
| 659 | link->resource[0]->flags |= IO_DATA_PATH_WIDTH_8; | 659 | link->config_flags |= CONF_ENABLE_IRQ | CONF_AUTO_SET_VPP | |
| 660 | link->resource[0]->end = 8; | 660 | CONF_AUTO_SET_IO; |
| 661 | |||
| 662 | link->config_flags |= CONF_ENABLE_IRQ | CONF_AUTO_SET_VPP; | ||
| 663 | 661 | ||
| 664 | return bt3c_config(link); | 662 | return bt3c_config(link); |
| 665 | } | 663 | } |
| @@ -673,38 +671,41 @@ static void bt3c_detach(struct pcmcia_device *link) | |||
| 673 | kfree(info); | 671 | kfree(info); |
| 674 | } | 672 | } |
| 675 | 673 | ||
| 676 | static int bt3c_check_config(struct pcmcia_device *p_dev, | 674 | static int bt3c_check_config(struct pcmcia_device *p_dev, void *priv_data) |
| 677 | cistpl_cftable_entry_t *cf, | ||
| 678 | cistpl_cftable_entry_t *dflt, | ||
| 679 | void *priv_data) | ||
| 680 | { | 675 | { |
| 681 | unsigned long try = (unsigned long) priv_data; | 676 | int *try = priv_data; |
| 682 | p_dev->io_lines = (try == 0) ? 16 : cf->io.flags & CISTPL_IO_LINES_MASK; | ||
| 683 | 677 | ||
| 684 | if ((cf->io.nwin > 0) && (cf->io.win[0].len == 8) && | 678 | if (try == 0) |
| 685 | (cf->io.win[0].base != 0)) { | 679 | p_dev->io_lines = 16; |
| 686 | p_dev->resource[0]->start = cf->io.win[0].base; | 680 | |
| 687 | if (!pcmcia_request_io(p_dev)) | 681 | if ((p_dev->resource[0]->end != 8) || (p_dev->resource[0]->start == 0)) |
| 688 | return 0; | 682 | return -EINVAL; |
| 689 | } | 683 | |
| 690 | return -ENODEV; | 684 | p_dev->resource[0]->end = 8; |
| 685 | p_dev->resource[0]->flags &= ~IO_DATA_PATH_WIDTH; | ||
| 686 | p_dev->resource[0]->flags |= IO_DATA_PATH_WIDTH_8; | ||
| 687 | |||
| 688 | return pcmcia_request_io(p_dev); | ||
| 691 | } | 689 | } |
| 692 | 690 | ||
| 693 | static int bt3c_check_config_notpicky(struct pcmcia_device *p_dev, | 691 | static int bt3c_check_config_notpicky(struct pcmcia_device *p_dev, |
| 694 | cistpl_cftable_entry_t *cf, | ||
| 695 | cistpl_cftable_entry_t *dflt, | ||
| 696 | void *priv_data) | 692 | void *priv_data) |
| 697 | { | 693 | { |
| 698 | static unsigned int base[5] = { 0x3f8, 0x2f8, 0x3e8, 0x2e8, 0x0 }; | 694 | static unsigned int base[5] = { 0x3f8, 0x2f8, 0x3e8, 0x2e8, 0x0 }; |
| 699 | int j; | 695 | int j; |
| 700 | 696 | ||
| 701 | if ((cf->io.nwin > 0) && ((cf->io.flags & CISTPL_IO_LINES_MASK) <= 3)) { | 697 | if (p_dev->io_lines > 3) |
| 702 | for (j = 0; j < 5; j++) { | 698 | return -ENODEV; |
| 703 | p_dev->resource[0]->start = base[j]; | 699 | |
| 704 | p_dev->io_lines = base[j] ? 16 : 3; | 700 | p_dev->resource[0]->flags &= ~IO_DATA_PATH_WIDTH; |
| 705 | if (!pcmcia_request_io(p_dev)) | 701 | p_dev->resource[0]->flags |= IO_DATA_PATH_WIDTH_8; |
| 706 | return 0; | 702 | p_dev->resource[0]->end = 8; |
| 707 | } | 703 | |
| 704 | for (j = 0; j < 5; j++) { | ||
| 705 | p_dev->resource[0]->start = base[j]; | ||
| 706 | p_dev->io_lines = base[j] ? 16 : 3; | ||
| 707 | if (!pcmcia_request_io(p_dev)) | ||
| 708 | return 0; | ||
| 708 | } | 709 | } |
| 709 | return -ENODEV; | 710 | return -ENODEV; |
| 710 | } | 711 | } |
diff --git a/drivers/bluetooth/btuart_cs.c b/drivers/bluetooth/btuart_cs.c index 8a6864fc8c38..9f9bb69dc0a2 100644 --- a/drivers/bluetooth/btuart_cs.c +++ b/drivers/bluetooth/btuart_cs.c | |||
| @@ -585,10 +585,8 @@ static int btuart_probe(struct pcmcia_device *link) | |||
| 585 | info->p_dev = link; | 585 | info->p_dev = link; |
| 586 | link->priv = info; | 586 | link->priv = info; |
| 587 | 587 | ||
| 588 | link->resource[0]->flags |= IO_DATA_PATH_WIDTH_8; | 588 | link->config_flags |= CONF_ENABLE_IRQ | CONF_AUTO_SET_VPP | |
| 589 | link->resource[0]->end = 8; | 589 | CONF_AUTO_SET_IO; |
| 590 | |||
| 591 | link->config_flags |= CONF_ENABLE_IRQ | CONF_AUTO_SET_VPP; | ||
| 592 | 590 | ||
| 593 | return btuart_config(link); | 591 | return btuart_config(link); |
| 594 | } | 592 | } |
| @@ -602,38 +600,41 @@ static void btuart_detach(struct pcmcia_device *link) | |||
| 602 | kfree(info); | 600 | kfree(info); |
| 603 | } | 601 | } |
| 604 | 602 | ||
| 605 | static int btuart_check_config(struct pcmcia_device *p_dev, | 603 | static int btuart_check_config(struct pcmcia_device *p_dev, void *priv_data) |
| 606 | cistpl_cftable_entry_t *cf, | ||
| 607 | cistpl_cftable_entry_t *dflt, | ||
| 608 | void *priv_data) | ||
| 609 | { | 604 | { |
| 610 | int *try = priv_data; | 605 | int *try = priv_data; |
| 611 | p_dev->io_lines = (try == 0) ? 16 : cf->io.flags & CISTPL_IO_LINES_MASK; | ||
| 612 | 606 | ||
| 613 | if ((cf->io.nwin > 0) && (cf->io.win[0].len == 8) && | 607 | if (try == 0) |
| 614 | (cf->io.win[0].base != 0)) { | 608 | p_dev->io_lines = 16; |
| 615 | p_dev->resource[0]->start = cf->io.win[0].base; | 609 | |
| 616 | if (!pcmcia_request_io(p_dev)) | 610 | if ((p_dev->resource[0]->end != 8) || (p_dev->resource[0]->start == 0)) |
| 617 | return 0; | 611 | return -EINVAL; |
| 618 | } | 612 | |
| 619 | return -ENODEV; | 613 | p_dev->resource[0]->end = 8; |
| 614 | p_dev->resource[0]->flags &= ~IO_DATA_PATH_WIDTH; | ||
| 615 | p_dev->resource[0]->flags |= IO_DATA_PATH_WIDTH_8; | ||
| 616 | |||
| 617 | return pcmcia_request_io(p_dev); | ||
| 620 | } | 618 | } |
| 621 | 619 | ||
| 622 | static int btuart_check_config_notpicky(struct pcmcia_device *p_dev, | 620 | static int btuart_check_config_notpicky(struct pcmcia_device *p_dev, |
| 623 | cistpl_cftable_entry_t *cf, | ||
| 624 | cistpl_cftable_entry_t *dflt, | ||
| 625 | void *priv_data) | 621 | void *priv_data) |
| 626 | { | 622 | { |
| 627 | static unsigned int base[5] = { 0x3f8, 0x2f8, 0x3e8, 0x2e8, 0x0 }; | 623 | static unsigned int base[5] = { 0x3f8, 0x2f8, 0x3e8, 0x2e8, 0x0 }; |
| 628 | int j; | 624 | int j; |
| 629 | 625 | ||
| 630 | if ((cf->io.nwin > 0) && ((cf->io.flags & CISTPL_IO_LINES_MASK) <= 3)) { | 626 | if (p_dev->io_lines > 3) |
| 631 | for (j = 0; j < 5; j++) { | 627 | return -ENODEV; |
| 632 | p_dev->resource[0]->start = base[j]; | 628 | |
| 633 | p_dev->io_lines = base[j] ? 16 : 3; | 629 | p_dev->resource[0]->flags &= ~IO_DATA_PATH_WIDTH; |
| 634 | if (!pcmcia_request_io(p_dev)) | 630 | p_dev->resource[0]->flags |= IO_DATA_PATH_WIDTH_8; |
| 635 | return 0; | 631 | p_dev->resource[0]->end = 8; |
| 636 | } | 632 | |
| 633 | for (j = 0; j < 5; j++) { | ||
| 634 | p_dev->resource[0]->start = base[j]; | ||
| 635 | p_dev->io_lines = base[j] ? 16 : 3; | ||
| 636 | if (!pcmcia_request_io(p_dev)) | ||
| 637 | return 0; | ||
| 637 | } | 638 | } |
| 638 | return -ENODEV; | 639 | return -ENODEV; |
| 639 | } | 640 | } |
diff --git a/drivers/bluetooth/dtl1_cs.c b/drivers/bluetooth/dtl1_cs.c index 4620cc398676..12cd177132fc 100644 --- a/drivers/bluetooth/dtl1_cs.c +++ b/drivers/bluetooth/dtl1_cs.c | |||
| @@ -571,10 +571,7 @@ static int dtl1_probe(struct pcmcia_device *link) | |||
| 571 | info->p_dev = link; | 571 | info->p_dev = link; |
| 572 | link->priv = info; | 572 | link->priv = info; |
| 573 | 573 | ||
| 574 | link->resource[0]->flags |= IO_DATA_PATH_WIDTH_8; | 574 | link->config_flags |= CONF_ENABLE_IRQ | CONF_AUTO_SET_IO; |
| 575 | link->resource[0]->end = 8; | ||
| 576 | |||
| 577 | link->config_flags |= CONF_ENABLE_IRQ; | ||
| 578 | 575 | ||
| 579 | return dtl1_config(link); | 576 | return dtl1_config(link); |
| 580 | } | 577 | } |
| @@ -589,17 +586,14 @@ static void dtl1_detach(struct pcmcia_device *link) | |||
| 589 | kfree(info); | 586 | kfree(info); |
| 590 | } | 587 | } |
| 591 | 588 | ||
| 592 | static int dtl1_confcheck(struct pcmcia_device *p_dev, | 589 | static int dtl1_confcheck(struct pcmcia_device *p_dev, void *priv_data) |
| 593 | cistpl_cftable_entry_t *cf, | ||
| 594 | cistpl_cftable_entry_t *dflt, | ||
| 595 | void *priv_data) | ||
| 596 | { | 590 | { |
| 597 | if ((cf->io.nwin != 1) || (cf->io.win[0].len <= 8)) | 591 | if ((p_dev->resource[1]->end) || (p_dev->resource[1]->end < 8)) |
| 598 | return -ENODEV; | 592 | return -ENODEV; |
| 599 | 593 | ||
| 600 | p_dev->resource[0]->start = cf->io.win[0].base; | 594 | p_dev->resource[0]->flags &= ~IO_DATA_PATH_WIDTH; |
| 601 | p_dev->resource[0]->end = cf->io.win[0].len; /*yo */ | 595 | p_dev->resource[0]->flags |= IO_DATA_PATH_WIDTH_8; |
| 602 | p_dev->io_lines = cf->io.flags & CISTPL_IO_LINES_MASK; | 596 | |
| 603 | return pcmcia_request_io(p_dev); | 597 | return pcmcia_request_io(p_dev); |
| 604 | } | 598 | } |
| 605 | 599 | ||
diff --git a/drivers/char/pcmcia/cm4000_cs.c b/drivers/char/pcmcia/cm4000_cs.c index 0b2f3b9d261a..79de9ccb8caf 100644 --- a/drivers/char/pcmcia/cm4000_cs.c +++ b/drivers/char/pcmcia/cm4000_cs.c | |||
| @@ -1741,19 +1741,8 @@ static void cmm_cm4000_release(struct pcmcia_device * link) | |||
| 1741 | 1741 | ||
| 1742 | /*==== Interface to PCMCIA Layer =======================================*/ | 1742 | /*==== Interface to PCMCIA Layer =======================================*/ |
| 1743 | 1743 | ||
| 1744 | static int cm4000_config_check(struct pcmcia_device *p_dev, | 1744 | static int cm4000_config_check(struct pcmcia_device *p_dev, void *priv_data) |
| 1745 | cistpl_cftable_entry_t *cfg, | ||
| 1746 | cistpl_cftable_entry_t *dflt, | ||
| 1747 | void *priv_data) | ||
| 1748 | { | 1745 | { |
| 1749 | if (!cfg->io.nwin) | ||
| 1750 | return -ENODEV; | ||
| 1751 | |||
| 1752 | p_dev->resource[0]->start = cfg->io.win[0].base; | ||
| 1753 | p_dev->resource[0]->end = cfg->io.win[0].len; | ||
| 1754 | p_dev->resource[0]->flags |= pcmcia_io_cfg_data_width(cfg->io.flags); | ||
| 1755 | p_dev->io_lines = cfg->io.flags & CISTPL_IO_LINES_MASK; | ||
| 1756 | |||
| 1757 | return pcmcia_request_io(p_dev); | 1746 | return pcmcia_request_io(p_dev); |
| 1758 | } | 1747 | } |
| 1759 | 1748 | ||
| @@ -1761,6 +1750,8 @@ static int cm4000_config(struct pcmcia_device * link, int devno) | |||
| 1761 | { | 1750 | { |
| 1762 | struct cm4000_dev *dev; | 1751 | struct cm4000_dev *dev; |
| 1763 | 1752 | ||
| 1753 | link->config_flags |= CONF_AUTO_SET_IO; | ||
| 1754 | |||
| 1764 | /* read the config-tuples */ | 1755 | /* read the config-tuples */ |
| 1765 | if (pcmcia_loop_config(link, cm4000_config_check, NULL)) | 1756 | if (pcmcia_loop_config(link, cm4000_config_check, NULL)) |
| 1766 | goto cs_release; | 1757 | goto cs_release; |
diff --git a/drivers/char/pcmcia/cm4040_cs.c b/drivers/char/pcmcia/cm4040_cs.c index acf88d5c72b2..bf012d228a9e 100644 --- a/drivers/char/pcmcia/cm4040_cs.c +++ b/drivers/char/pcmcia/cm4040_cs.c | |||
| @@ -515,25 +515,9 @@ static void cm4040_reader_release(struct pcmcia_device *link) | |||
| 515 | return; | 515 | return; |
| 516 | } | 516 | } |
| 517 | 517 | ||
| 518 | static int cm4040_config_check(struct pcmcia_device *p_dev, | 518 | static int cm4040_config_check(struct pcmcia_device *p_dev, void *priv_data) |
| 519 | cistpl_cftable_entry_t *cfg, | ||
| 520 | cistpl_cftable_entry_t *dflt, | ||
| 521 | void *priv_data) | ||
| 522 | { | 519 | { |
| 523 | int rc; | 520 | return pcmcia_request_io(p_dev); |
| 524 | if (!cfg->io.nwin) | ||
| 525 | return -ENODEV; | ||
| 526 | |||
| 527 | /* Get the IOaddr */ | ||
| 528 | p_dev->resource[0]->start = cfg->io.win[0].base; | ||
| 529 | p_dev->resource[0]->end = cfg->io.win[0].len; | ||
| 530 | p_dev->resource[0]->flags |= pcmcia_io_cfg_data_width(cfg->io.flags); | ||
| 531 | p_dev->io_lines = cfg->io.flags & CISTPL_IO_LINES_MASK; | ||
| 532 | rc = pcmcia_request_io(p_dev); | ||
| 533 | |||
| 534 | dev_printk(KERN_INFO, &p_dev->dev, | ||
| 535 | "pcmcia_request_io returned 0x%x\n", rc); | ||
| 536 | return rc; | ||
| 537 | } | 521 | } |
| 538 | 522 | ||
| 539 | 523 | ||
| @@ -542,6 +526,8 @@ static int reader_config(struct pcmcia_device *link, int devno) | |||
| 542 | struct reader_dev *dev; | 526 | struct reader_dev *dev; |
| 543 | int fail_rc; | 527 | int fail_rc; |
| 544 | 528 | ||
| 529 | link->config_flags |= CONF_AUTO_SET_IO; | ||
| 530 | |||
| 545 | if (pcmcia_loop_config(link, cm4040_config_check, NULL)) | 531 | if (pcmcia_loop_config(link, cm4040_config_check, NULL)) |
| 546 | goto cs_release; | 532 | goto cs_release; |
| 547 | 533 | ||
diff --git a/drivers/char/pcmcia/ipwireless/main.c b/drivers/char/pcmcia/ipwireless/main.c index 1b7f0920737b..594c23be69f5 100644 --- a/drivers/char/pcmcia/ipwireless/main.c +++ b/drivers/char/pcmcia/ipwireless/main.c | |||
| @@ -75,22 +75,18 @@ static void signalled_reboot_callback(void *callback_data) | |||
| 75 | schedule_work(&ipw->work_reboot); | 75 | schedule_work(&ipw->work_reboot); |
| 76 | } | 76 | } |
| 77 | 77 | ||
| 78 | static int ipwireless_probe(struct pcmcia_device *p_dev, | 78 | static int ipwireless_probe(struct pcmcia_device *p_dev, void *priv_data) |
| 79 | cistpl_cftable_entry_t *cfg, | ||
| 80 | cistpl_cftable_entry_t *dflt, | ||
| 81 | void *priv_data) | ||
| 82 | { | 79 | { |
| 83 | struct ipw_dev *ipw = priv_data; | 80 | struct ipw_dev *ipw = priv_data; |
| 84 | struct resource *io_resource; | 81 | struct resource *io_resource; |
| 85 | int ret; | 82 | int ret; |
| 86 | 83 | ||
| 84 | p_dev->resource[0]->flags &= ~IO_DATA_PATH_WIDTH; | ||
| 87 | p_dev->resource[0]->flags |= IO_DATA_PATH_WIDTH_AUTO; | 85 | p_dev->resource[0]->flags |= IO_DATA_PATH_WIDTH_AUTO; |
| 88 | p_dev->resource[0]->start = cfg->io.win[0].base; | ||
| 89 | p_dev->resource[0]->end = cfg->io.win[0].len; | ||
| 90 | 86 | ||
| 91 | /* 0x40 causes it to generate level mode interrupts. */ | 87 | /* 0x40 causes it to generate level mode interrupts. */ |
| 92 | /* 0x04 enables IREQ pin. */ | 88 | /* 0x04 enables IREQ pin. */ |
| 93 | p_dev->config_index = cfg->index | 0x44; | 89 | p_dev->config_index |= 0x44; |
| 94 | p_dev->io_lines = 16; | 90 | p_dev->io_lines = 16; |
| 95 | ret = pcmcia_request_io(p_dev); | 91 | ret = pcmcia_request_io(p_dev); |
| 96 | if (ret) | 92 | if (ret) |
| @@ -100,26 +96,18 @@ static int ipwireless_probe(struct pcmcia_device *p_dev, | |||
| 100 | resource_size(p_dev->resource[0]), | 96 | resource_size(p_dev->resource[0]), |
| 101 | IPWIRELESS_PCCARD_NAME); | 97 | IPWIRELESS_PCCARD_NAME); |
| 102 | 98 | ||
| 103 | if (cfg->mem.nwin == 0) | ||
| 104 | return 0; | ||
| 105 | |||
| 106 | p_dev->resource[2]->flags |= | 99 | p_dev->resource[2]->flags |= |
| 107 | WIN_DATA_WIDTH_16 | WIN_MEMORY_TYPE_CM | WIN_ENABLE; | 100 | WIN_DATA_WIDTH_16 | WIN_MEMORY_TYPE_CM | WIN_ENABLE; |
| 108 | p_dev->resource[2]->start = cfg->mem.win[0].host_addr; | ||
| 109 | p_dev->resource[2]->end = cfg->mem.win[0].len; | ||
| 110 | if (p_dev->resource[2]->end < 0x1000) | ||
| 111 | p_dev->resource[2]->end = 0x1000; | ||
| 112 | 101 | ||
| 113 | ret = pcmcia_request_window(p_dev, p_dev->resource[2], 0); | 102 | ret = pcmcia_request_window(p_dev, p_dev->resource[2], 0); |
| 114 | if (ret != 0) | 103 | if (ret != 0) |
| 115 | goto exit1; | 104 | goto exit1; |
| 116 | 105 | ||
| 117 | ret = pcmcia_map_mem_page(p_dev, p_dev->resource[2], | 106 | ret = pcmcia_map_mem_page(p_dev, p_dev->resource[2], p_dev->card_addr); |
| 118 | cfg->mem.win[0].card_addr); | ||
| 119 | if (ret != 0) | 107 | if (ret != 0) |
| 120 | goto exit2; | 108 | goto exit2; |
| 121 | 109 | ||
| 122 | ipw->is_v2_card = cfg->mem.win[0].len == 0x100; | 110 | ipw->is_v2_card = resource_size(p_dev->resource[2]) == 0x100; |
| 123 | 111 | ||
| 124 | ipw->attr_memory = ioremap(p_dev->resource[2]->start, | 112 | ipw->attr_memory = ioremap(p_dev->resource[2]->start, |
| 125 | resource_size(p_dev->resource[2])); | 113 | resource_size(p_dev->resource[2])); |
| @@ -165,13 +153,13 @@ static int config_ipwireless(struct ipw_dev *ipw) | |||
| 165 | int ret = 0; | 153 | int ret = 0; |
| 166 | 154 | ||
| 167 | ipw->is_v2_card = 0; | 155 | ipw->is_v2_card = 0; |
| 156 | link->config_flags |= CONF_AUTO_SET_IO | CONF_AUTO_SET_IOMEM | | ||
| 157 | CONF_ENABLE_IRQ; | ||
| 168 | 158 | ||
| 169 | ret = pcmcia_loop_config(link, ipwireless_probe, ipw); | 159 | ret = pcmcia_loop_config(link, ipwireless_probe, ipw); |
| 170 | if (ret != 0) | 160 | if (ret != 0) |
| 171 | return ret; | 161 | return ret; |
| 172 | 162 | ||
| 173 | link->config_flags |= CONF_ENABLE_IRQ; | ||
| 174 | |||
| 175 | INIT_WORK(&ipw->work_reboot, signalled_reboot_work); | 163 | INIT_WORK(&ipw->work_reboot, signalled_reboot_work); |
| 176 | 164 | ||
| 177 | ipwireless_init_hardware_v1(ipw->hardware, link->resource[0]->start, | 165 | ipwireless_init_hardware_v1(ipw->hardware, link->resource[0]->start, |
diff --git a/drivers/char/pcmcia/synclink_cs.c b/drivers/char/pcmcia/synclink_cs.c index c701434f76b7..a343b8f817e4 100644 --- a/drivers/char/pcmcia/synclink_cs.c +++ b/drivers/char/pcmcia/synclink_cs.c | |||
| @@ -561,19 +561,8 @@ static int mgslpc_probe(struct pcmcia_device *link) | |||
| 561 | /* Card has been inserted. | 561 | /* Card has been inserted. |
| 562 | */ | 562 | */ |
| 563 | 563 | ||
| 564 | static int mgslpc_ioprobe(struct pcmcia_device *p_dev, | 564 | static int mgslpc_ioprobe(struct pcmcia_device *p_dev, void *priv_data) |
| 565 | cistpl_cftable_entry_t *cfg, | ||
| 566 | cistpl_cftable_entry_t *dflt, | ||
| 567 | void *priv_data) | ||
| 568 | { | 565 | { |
| 569 | if (!cfg->io.nwin) | ||
| 570 | return -ENODEV; | ||
| 571 | |||
| 572 | p_dev->resource[0]->start = cfg->io.win[0].base; | ||
| 573 | p_dev->resource[0]->end = cfg->io.win[0].len; | ||
| 574 | p_dev->resource[0]->flags |= pcmcia_io_cfg_data_width(cfg->io.flags); | ||
| 575 | p_dev->io_lines = cfg->io.flags & CISTPL_IO_LINES_MASK; | ||
| 576 | |||
| 577 | return pcmcia_request_io(p_dev); | 566 | return pcmcia_request_io(p_dev); |
| 578 | } | 567 | } |
| 579 | 568 | ||
| @@ -585,11 +574,12 @@ static int mgslpc_config(struct pcmcia_device *link) | |||
| 585 | if (debug_level >= DEBUG_LEVEL_INFO) | 574 | if (debug_level >= DEBUG_LEVEL_INFO) |
| 586 | printk("mgslpc_config(0x%p)\n", link); | 575 | printk("mgslpc_config(0x%p)\n", link); |
| 587 | 576 | ||
| 577 | link->config_flags |= CONF_ENABLE_IRQ | CONF_AUTO_SET_IO; | ||
| 578 | |||
| 588 | ret = pcmcia_loop_config(link, mgslpc_ioprobe, NULL); | 579 | ret = pcmcia_loop_config(link, mgslpc_ioprobe, NULL); |
| 589 | if (ret != 0) | 580 | if (ret != 0) |
| 590 | goto failed; | 581 | goto failed; |
| 591 | 582 | ||
| 592 | link->config_flags |= CONF_ENABLE_IRQ; | ||
| 593 | link->config_index = 8; | 583 | link->config_index = 8; |
| 594 | link->config_regs = PRESENT_OPTION; | 584 | link->config_regs = PRESENT_OPTION; |
| 595 | 585 | ||
diff --git a/drivers/ide/ide-cs.c b/drivers/ide/ide-cs.c index 25b8a105a98d..c389d9a28881 100644 --- a/drivers/ide/ide-cs.c +++ b/drivers/ide/ide-cs.c | |||
| @@ -96,10 +96,8 @@ static int ide_probe(struct pcmcia_device *link) | |||
| 96 | info->p_dev = link; | 96 | info->p_dev = link; |
| 97 | link->priv = info; | 97 | link->priv = info; |
| 98 | 98 | ||
| 99 | link->resource[0]->flags |= IO_DATA_PATH_WIDTH_AUTO; | 99 | link->config_flags |= CONF_ENABLE_IRQ | CONF_AUTO_SET_IO | |
| 100 | link->resource[1]->flags |= IO_DATA_PATH_WIDTH_8; | 100 | CONF_AUTO_SET_VPP | CONF_AUTO_CHECK_VCC; |
| 101 | link->config_flags |= CONF_ENABLE_IRQ; | ||
| 102 | link->config_flags |= CONF_AUTO_SET_VPP | CONF_AUTO_CHECK_VCC; | ||
| 103 | 101 | ||
| 104 | return ide_config(link); | 102 | return ide_config(link); |
| 105 | } /* ide_attach */ | 103 | } /* ide_attach */ |
| @@ -194,52 +192,31 @@ out_release: | |||
| 194 | 192 | ||
| 195 | ======================================================================*/ | 193 | ======================================================================*/ |
| 196 | 194 | ||
| 197 | struct pcmcia_config_check { | 195 | static int pcmcia_check_one_config(struct pcmcia_device *pdev, void *priv_data) |
| 198 | unsigned long ctl_base; | ||
| 199 | int is_kme; | ||
| 200 | }; | ||
| 201 | |||
| 202 | static int pcmcia_check_one_config(struct pcmcia_device *pdev, | ||
| 203 | cistpl_cftable_entry_t *cfg, | ||
| 204 | cistpl_cftable_entry_t *dflt, | ||
| 205 | void *priv_data) | ||
| 206 | { | 196 | { |
| 207 | struct pcmcia_config_check *stk = priv_data; | 197 | int *is_kme = priv_data; |
| 208 | 198 | ||
| 209 | if ((cfg->io.nwin > 0) || (dflt->io.nwin > 0)) { | 199 | if (!(pdev->resource[0]->flags & IO_DATA_PATH_WIDTH_8)) { |
| 210 | cistpl_io_t *io = (cfg->io.nwin) ? &cfg->io : &dflt->io; | 200 | pdev->resource[0]->flags &= ~IO_DATA_PATH_WIDTH; |
| 211 | pdev->io_lines = io->flags & CISTPL_IO_LINES_MASK; | 201 | pdev->resource[0]->flags |= IO_DATA_PATH_WIDTH_AUTO; |
| 212 | pdev->config_index = cfg->index; | 202 | } |
| 213 | pdev->resource[0]->start = io->win[0].base; | 203 | pdev->resource[1]->flags &= ~IO_DATA_PATH_WIDTH; |
| 214 | if (!(io->flags & CISTPL_IO_16BIT)) { | 204 | pdev->resource[1]->flags |= IO_DATA_PATH_WIDTH_8; |
| 215 | pdev->resource[0]->flags &= ~IO_DATA_PATH_WIDTH; | 205 | |
| 216 | pdev->resource[0]->flags |= IO_DATA_PATH_WIDTH_8; | 206 | if (pdev->resource[1]->end) { |
| 217 | } | 207 | pdev->resource[0]->end = 8; |
| 218 | if (io->nwin == 2) { | 208 | pdev->resource[1]->end = (*is_kme) ? 2 : 1; |
| 219 | pdev->resource[0]->end = 8; | 209 | } else { |
| 220 | pdev->resource[1]->start = io->win[1].base; | 210 | if (pdev->resource[0]->end < 16) |
| 221 | pdev->resource[1]->end = (stk->is_kme) ? 2 : 1; | ||
| 222 | if (pcmcia_request_io(pdev) != 0) | ||
| 223 | return -ENODEV; | ||
| 224 | stk->ctl_base = pdev->resource[1]->start; | ||
| 225 | } else if ((io->nwin == 1) && (io->win[0].len >= 16)) { | ||
| 226 | pdev->resource[0]->end = io->win[0].len; | ||
| 227 | pdev->resource[1]->end = 0; | ||
| 228 | if (pcmcia_request_io(pdev) != 0) | ||
| 229 | return -ENODEV; | ||
| 230 | stk->ctl_base = pdev->resource[0]->start + 0x0e; | ||
| 231 | } else | ||
| 232 | return -ENODEV; | 211 | return -ENODEV; |
| 233 | /* If we've got this far, we're done */ | ||
| 234 | return 0; | ||
| 235 | } | 212 | } |
| 236 | return -ENODEV; | 213 | |
| 214 | return pcmcia_request_io(pdev); | ||
| 237 | } | 215 | } |
| 238 | 216 | ||
| 239 | static int ide_config(struct pcmcia_device *link) | 217 | static int ide_config(struct pcmcia_device *link) |
| 240 | { | 218 | { |
| 241 | ide_info_t *info = link->priv; | 219 | ide_info_t *info = link->priv; |
| 242 | struct pcmcia_config_check *stk = NULL; | ||
| 243 | int ret = 0, is_kme = 0; | 220 | int ret = 0, is_kme = 0; |
| 244 | unsigned long io_base, ctl_base; | 221 | unsigned long io_base, ctl_base; |
| 245 | struct ide_host *host; | 222 | struct ide_host *host; |
| @@ -250,19 +227,16 @@ static int ide_config(struct pcmcia_device *link) | |||
| 250 | ((link->card_id == PRODID_KME_KXLC005_A) || | 227 | ((link->card_id == PRODID_KME_KXLC005_A) || |
| 251 | (link->card_id == PRODID_KME_KXLC005_B))); | 228 | (link->card_id == PRODID_KME_KXLC005_B))); |
| 252 | 229 | ||
| 253 | stk = kzalloc(sizeof(*stk), GFP_KERNEL); | 230 | if (pcmcia_loop_config(link, pcmcia_check_one_config, &is_kme)) { |
| 254 | if (!stk) | ||
| 255 | goto err_mem; | ||
| 256 | stk->is_kme = is_kme; | ||
| 257 | io_base = ctl_base = 0; | ||
| 258 | |||
| 259 | if (pcmcia_loop_config(link, pcmcia_check_one_config, stk)) { | ||
| 260 | link->config_flags &= ~CONF_AUTO_CHECK_VCC; | 231 | link->config_flags &= ~CONF_AUTO_CHECK_VCC; |
| 261 | if (pcmcia_loop_config(link, pcmcia_check_one_config, stk)) | 232 | if (pcmcia_loop_config(link, pcmcia_check_one_config, &is_kme)) |
| 262 | goto failed; /* No suitable config found */ | 233 | goto failed; /* No suitable config found */ |
| 263 | } | 234 | } |
| 264 | io_base = link->resource[0]->start; | 235 | io_base = link->resource[0]->start; |
| 265 | ctl_base = stk->ctl_base; | 236 | if (link->resource[1]->end) |
| 237 | ctl_base = link->resource[1]->start; | ||
| 238 | else | ||
| 239 | ctl_base = link->resource[0]->start + 0x0e; | ||
| 266 | 240 | ||
| 267 | if (!link->irq) | 241 | if (!link->irq) |
| 268 | goto failed; | 242 | goto failed; |
| @@ -294,15 +268,9 @@ static int ide_config(struct pcmcia_device *link) | |||
| 294 | 'a' + host->ports[0]->index * 2, | 268 | 'a' + host->ports[0]->index * 2, |
| 295 | link->vpp / 10, link->vpp % 10); | 269 | link->vpp / 10, link->vpp % 10); |
| 296 | 270 | ||
| 297 | kfree(stk); | ||
| 298 | return 0; | 271 | return 0; |
| 299 | 272 | ||
| 300 | err_mem: | ||
| 301 | printk(KERN_NOTICE "ide-cs: ide_config failed memory allocation\n"); | ||
| 302 | goto failed; | ||
| 303 | |||
| 304 | failed: | 273 | failed: |
| 305 | kfree(stk); | ||
| 306 | ide_release(link); | 274 | ide_release(link); |
| 307 | return -ENODEV; | 275 | return -ENODEV; |
| 308 | } /* ide_config */ | 276 | } /* ide_config */ |
diff --git a/drivers/isdn/hardware/avm/avm_cs.c b/drivers/isdn/hardware/avm/avm_cs.c index 9dbab9c99bea..403a995bec95 100644 --- a/drivers/isdn/hardware/avm/avm_cs.c +++ b/drivers/isdn/hardware/avm/avm_cs.c | |||
| @@ -72,13 +72,8 @@ static void avmcs_detach(struct pcmcia_device *p_dev); | |||
| 72 | 72 | ||
| 73 | static int avmcs_probe(struct pcmcia_device *p_dev) | 73 | static int avmcs_probe(struct pcmcia_device *p_dev) |
| 74 | { | 74 | { |
| 75 | |||
| 76 | /* The io structure describes IO port mapping */ | ||
| 77 | p_dev->resource[0]->end = 16; | ||
| 78 | p_dev->resource[0]->flags |= IO_DATA_PATH_WIDTH_8; | ||
| 79 | |||
| 80 | /* General socket configuration */ | 75 | /* General socket configuration */ |
| 81 | p_dev->config_flags |= CONF_ENABLE_IRQ; | 76 | p_dev->config_flags |= CONF_ENABLE_IRQ | CONF_AUTO_SET_IO; |
| 82 | p_dev->config_index = 1; | 77 | p_dev->config_index = 1; |
| 83 | p_dev->config_regs = PRESENT_OPTION; | 78 | p_dev->config_regs = PRESENT_OPTION; |
| 84 | 79 | ||
| @@ -107,16 +102,12 @@ static void avmcs_detach(struct pcmcia_device *link) | |||
| 107 | 102 | ||
| 108 | ======================================================================*/ | 103 | ======================================================================*/ |
| 109 | 104 | ||
| 110 | static int avmcs_configcheck(struct pcmcia_device *p_dev, | 105 | static int avmcs_configcheck(struct pcmcia_device *p_dev, void *priv_data) |
| 111 | cistpl_cftable_entry_t *cf, | ||
| 112 | cistpl_cftable_entry_t *dflt, | ||
| 113 | void *priv_data) | ||
| 114 | { | 106 | { |
| 115 | if (cf->io.nwin <= 0) | 107 | p_dev->resource[0]->end = 16; |
| 116 | return -ENODEV; | 108 | p_dev->resource[0]->flags &= ~IO_DATA_PATH_WIDTH; |
| 109 | p_dev->resource[0]->flags |= IO_DATA_PATH_WIDTH_8; | ||
| 117 | 110 | ||
| 118 | p_dev->resource[0]->start = cf->io.win[0].base; | ||
| 119 | p_dev->resource[0]->end = cf->io.win[0].len; | ||
| 120 | return pcmcia_request_io(p_dev); | 111 | return pcmcia_request_io(p_dev); |
| 121 | } | 112 | } |
| 122 | 113 | ||
diff --git a/drivers/isdn/hisax/avma1_cs.c b/drivers/isdn/hisax/avma1_cs.c index 2f2b0005f07b..cb09f0cacd12 100644 --- a/drivers/isdn/hisax/avma1_cs.c +++ b/drivers/isdn/hisax/avma1_cs.c | |||
| @@ -76,14 +76,8 @@ static int __devinit avma1cs_probe(struct pcmcia_device *p_dev) | |||
| 76 | { | 76 | { |
| 77 | dev_dbg(&p_dev->dev, "avma1cs_attach()\n"); | 77 | dev_dbg(&p_dev->dev, "avma1cs_attach()\n"); |
| 78 | 78 | ||
| 79 | /* The io structure describes IO port mapping */ | ||
| 80 | p_dev->resource[0]->end = 16; | ||
| 81 | p_dev->resource[0]->flags |= IO_DATA_PATH_WIDTH_8; | ||
| 82 | p_dev->resource[1]->end = 16; | ||
| 83 | p_dev->resource[1]->flags |= IO_DATA_PATH_WIDTH_16; | ||
| 84 | |||
| 85 | /* General socket configuration */ | 79 | /* General socket configuration */ |
| 86 | p_dev->config_flags |= CONF_ENABLE_IRQ; | 80 | p_dev->config_flags |= CONF_ENABLE_IRQ | CONF_AUTO_SET_IO; |
| 87 | p_dev->config_index = 1; | 81 | p_dev->config_index = 1; |
| 88 | p_dev->config_regs = PRESENT_OPTION; | 82 | p_dev->config_regs = PRESENT_OPTION; |
| 89 | 83 | ||
| @@ -114,17 +108,13 @@ static void __devexit avma1cs_detach(struct pcmcia_device *link) | |||
| 114 | 108 | ||
| 115 | ======================================================================*/ | 109 | ======================================================================*/ |
| 116 | 110 | ||
| 117 | static int avma1cs_configcheck(struct pcmcia_device *p_dev, | 111 | static int avma1cs_configcheck(struct pcmcia_device *p_dev, void *priv_data) |
| 118 | cistpl_cftable_entry_t *cf, | ||
| 119 | cistpl_cftable_entry_t *dflt, | ||
| 120 | void *priv_data) | ||
| 121 | { | 112 | { |
| 122 | if (cf->io.nwin <= 0) | 113 | p_dev->resource[0]->end = 16; |
| 123 | return -ENODEV; | 114 | p_dev->resource[0]->flags &= ~IO_DATA_PATH_WIDTH; |
| 124 | 115 | p_dev->resource[0]->flags |= IO_DATA_PATH_WIDTH_8; | |
| 125 | p_dev->resource[0]->start = cf->io.win[0].base; | ||
| 126 | p_dev->resource[0]->end = cf->io.win[0].len; | ||
| 127 | p_dev->io_lines = 5; | 116 | p_dev->io_lines = 5; |
| 117 | |||
| 128 | return pcmcia_request_io(p_dev); | 118 | return pcmcia_request_io(p_dev); |
| 129 | } | 119 | } |
| 130 | 120 | ||
diff --git a/drivers/isdn/hisax/elsa_cs.c b/drivers/isdn/hisax/elsa_cs.c index 0a65280be8d5..f203a52aab2a 100644 --- a/drivers/isdn/hisax/elsa_cs.c +++ b/drivers/isdn/hisax/elsa_cs.c | |||
| @@ -118,16 +118,6 @@ static int __devinit elsa_cs_probe(struct pcmcia_device *link) | |||
| 118 | 118 | ||
| 119 | local->cardnr = -1; | 119 | local->cardnr = -1; |
| 120 | 120 | ||
| 121 | /* | ||
| 122 | General socket configuration defaults can go here. In this | ||
| 123 | client, we assume very little, and rely on the CIS for almost | ||
| 124 | everything. In most clients, many details (i.e., number, sizes, | ||
| 125 | and attributes of IO windows) are fixed by the nature of the | ||
| 126 | device, and can be hard-wired here. | ||
| 127 | */ | ||
| 128 | link->resource[0]->end = 8; | ||
| 129 | link->resource[0]->flags |= IO_DATA_PATH_WIDTH_AUTO; | ||
| 130 | |||
| 131 | return elsa_cs_config(link); | 121 | return elsa_cs_config(link); |
| 132 | } /* elsa_cs_attach */ | 122 | } /* elsa_cs_attach */ |
| 133 | 123 | ||
| @@ -160,18 +150,17 @@ static void __devexit elsa_cs_detach(struct pcmcia_device *link) | |||
| 160 | 150 | ||
| 161 | ======================================================================*/ | 151 | ======================================================================*/ |
| 162 | 152 | ||
| 163 | static int elsa_cs_configcheck(struct pcmcia_device *p_dev, | 153 | static int elsa_cs_configcheck(struct pcmcia_device *p_dev, void *priv_data) |
| 164 | cistpl_cftable_entry_t *cf, | ||
| 165 | cistpl_cftable_entry_t *dflt, | ||
| 166 | void *priv_data) | ||
| 167 | { | 154 | { |
| 168 | int j; | 155 | int j; |
| 169 | 156 | ||
| 170 | p_dev->io_lines = 3; | 157 | p_dev->io_lines = 3; |
| 158 | p_dev->resource[0]->end = 8; | ||
| 159 | p_dev->resource[0]->flags &= IO_DATA_PATH_WIDTH; | ||
| 160 | p_dev->resource[0]->flags |= IO_DATA_PATH_WIDTH_AUTO; | ||
| 171 | 161 | ||
| 172 | if ((cf->io.nwin > 0) && cf->io.win[0].base) { | 162 | if ((p_dev->resource[0]->end) && p_dev->resource[0]->start) { |
| 173 | printk(KERN_INFO "(elsa_cs: looks like the 96 model)\n"); | 163 | printk(KERN_INFO "(elsa_cs: looks like the 96 model)\n"); |
| 174 | p_dev->resource[0]->start = cf->io.win[0].base; | ||
| 175 | if (!pcmcia_request_io(p_dev)) | 164 | if (!pcmcia_request_io(p_dev)) |
| 176 | return 0; | 165 | return 0; |
| 177 | } else { | 166 | } else { |
| @@ -194,6 +183,8 @@ static int __devinit elsa_cs_config(struct pcmcia_device *link) | |||
| 194 | dev_dbg(&link->dev, "elsa_config(0x%p)\n", link); | 183 | dev_dbg(&link->dev, "elsa_config(0x%p)\n", link); |
| 195 | dev = link->priv; | 184 | dev = link->priv; |
| 196 | 185 | ||
| 186 | link->config_flags |= CONF_ENABLE_IRQ | CONF_AUTO_SET_IO; | ||
| 187 | |||
| 197 | i = pcmcia_loop_config(link, elsa_cs_configcheck, NULL); | 188 | i = pcmcia_loop_config(link, elsa_cs_configcheck, NULL); |
| 198 | if (i != 0) | 189 | if (i != 0) |
| 199 | goto failed; | 190 | goto failed; |
diff --git a/drivers/isdn/hisax/sedlbauer_cs.c b/drivers/isdn/hisax/sedlbauer_cs.c index b69eccfdbb05..a88c88f6cdeb 100644 --- a/drivers/isdn/hisax/sedlbauer_cs.c +++ b/drivers/isdn/hisax/sedlbauer_cs.c | |||
| @@ -128,8 +128,6 @@ static int __devinit sedlbauer_probe(struct pcmcia_device *link) | |||
| 128 | /* from old sedl_cs | 128 | /* from old sedl_cs |
| 129 | */ | 129 | */ |
| 130 | /* The io structure describes IO port mapping */ | 130 | /* The io structure describes IO port mapping */ |
| 131 | link->resource[0]->end = 8; | ||
| 132 | link->resource[0]->flags |= IO_DATA_PATH_WIDTH_8; | ||
| 133 | 131 | ||
| 134 | return sedlbauer_config(link); | 132 | return sedlbauer_config(link); |
| 135 | } /* sedlbauer_attach */ | 133 | } /* sedlbauer_attach */ |
| @@ -161,35 +159,13 @@ static void __devexit sedlbauer_detach(struct pcmcia_device *link) | |||
| 161 | device available to the system. | 159 | device available to the system. |
| 162 | 160 | ||
| 163 | ======================================================================*/ | 161 | ======================================================================*/ |
| 164 | static int sedlbauer_config_check(struct pcmcia_device *p_dev, | 162 | static int sedlbauer_config_check(struct pcmcia_device *p_dev, void *priv_data) |
| 165 | cistpl_cftable_entry_t *cfg, | ||
| 166 | cistpl_cftable_entry_t *dflt, | ||
| 167 | void *priv_data) | ||
| 168 | { | 163 | { |
| 169 | if (cfg->index == 0) | 164 | if (p_dev->config_index == 0) |
| 170 | return -ENODEV; | 165 | return -EINVAL; |
| 171 | |||
| 172 | /* IO window settings */ | ||
| 173 | p_dev->resource[0]->end = p_dev->resource[1]->end = 0; | ||
| 174 | if ((cfg->io.nwin > 0) || (dflt->io.nwin > 0)) { | ||
| 175 | cistpl_io_t *io = (cfg->io.nwin) ? &cfg->io : &dflt->io; | ||
| 176 | p_dev->resource[0]->start = io->win[0].base; | ||
| 177 | p_dev->resource[0]->end = io->win[0].len; | ||
| 178 | p_dev->resource[0]->flags &= ~IO_DATA_PATH_WIDTH; | ||
| 179 | p_dev->resource[0]->flags |= | ||
| 180 | pcmcia_io_cfg_data_width(io->flags); | ||
| 181 | if (io->nwin > 1) { | ||
| 182 | p_dev->resource[1]->flags = p_dev->resource[0]->flags; | ||
| 183 | p_dev->resource[1]->start = io->win[1].base; | ||
| 184 | p_dev->resource[1]->end = io->win[1].len; | ||
| 185 | } | ||
| 186 | /* This reserves IO space but doesn't actually enable it */ | ||
| 187 | p_dev->io_lines = 3; | ||
| 188 | if (pcmcia_request_io(p_dev) != 0) | ||
| 189 | return -ENODEV; | ||
| 190 | } | ||
| 191 | 166 | ||
| 192 | return 0; | 167 | p_dev->io_lines = 3; |
| 168 | return pcmcia_request_io(p_dev); | ||
| 193 | } | 169 | } |
| 194 | 170 | ||
| 195 | 171 | ||
| @@ -202,7 +178,7 @@ static int __devinit sedlbauer_config(struct pcmcia_device *link) | |||
| 202 | dev_dbg(&link->dev, "sedlbauer_config(0x%p)\n", link); | 178 | dev_dbg(&link->dev, "sedlbauer_config(0x%p)\n", link); |
| 203 | 179 | ||
| 204 | link->config_flags |= CONF_ENABLE_IRQ | CONF_AUTO_CHECK_VCC | | 180 | link->config_flags |= CONF_ENABLE_IRQ | CONF_AUTO_CHECK_VCC | |
| 205 | CONF_AUTO_SET_VPP | CONF_AUTO_AUDIO; | 181 | CONF_AUTO_SET_VPP | CONF_AUTO_AUDIO | CONF_AUTO_SET_IO; |
| 206 | 182 | ||
| 207 | /* | 183 | /* |
| 208 | In this loop, we scan the CIS for configuration table entries, | 184 | In this loop, we scan the CIS for configuration table entries, |
diff --git a/drivers/isdn/hisax/teles_cs.c b/drivers/isdn/hisax/teles_cs.c index 6605480aa37f..05a5631963bb 100644 --- a/drivers/isdn/hisax/teles_cs.c +++ b/drivers/isdn/hisax/teles_cs.c | |||
| @@ -105,10 +105,7 @@ static int __devinit teles_probe(struct pcmcia_device *link) | |||
| 105 | and attributes of IO windows) are fixed by the nature of the | 105 | and attributes of IO windows) are fixed by the nature of the |
| 106 | device, and can be hard-wired here. | 106 | device, and can be hard-wired here. |
| 107 | */ | 107 | */ |
| 108 | link->resource[0]->end = 96; | 108 | link->config_flags |= CONF_ENABLE_IRQ | CONF_AUTO_SET_IO; |
| 109 | link->resource[0]->flags |= IO_DATA_PATH_WIDTH_AUTO; | ||
| 110 | |||
| 111 | link->config_flags |= CONF_ENABLE_IRQ; | ||
| 112 | 109 | ||
| 113 | return teles_cs_config(link); | 110 | return teles_cs_config(link); |
| 114 | } /* teles_attach */ | 111 | } /* teles_attach */ |
| @@ -142,18 +139,17 @@ static void __devexit teles_detach(struct pcmcia_device *link) | |||
| 142 | 139 | ||
| 143 | ======================================================================*/ | 140 | ======================================================================*/ |
| 144 | 141 | ||
| 145 | static int teles_cs_configcheck(struct pcmcia_device *p_dev, | 142 | static int teles_cs_configcheck(struct pcmcia_device *p_dev, void *priv_data) |
| 146 | cistpl_cftable_entry_t *cf, | ||
| 147 | cistpl_cftable_entry_t *dflt, | ||
| 148 | void *priv_data) | ||
| 149 | { | 143 | { |
| 150 | int j; | 144 | int j; |
| 151 | 145 | ||
| 152 | p_dev->io_lines = 5; | 146 | p_dev->io_lines = 5; |
| 147 | p_dev->resource[0]->end = 96; | ||
| 148 | p_dev->resource[0]->flags &= IO_DATA_PATH_WIDTH; | ||
| 149 | p_dev->resource[0]->flags |= IO_DATA_PATH_WIDTH_AUTO; | ||
| 153 | 150 | ||
| 154 | if ((cf->io.nwin > 0) && cf->io.win[0].base) { | 151 | if ((p_dev->resource[0]->end) && p_dev->resource[0]->start) { |
| 155 | printk(KERN_INFO "(teles_cs: looks like the 96 model)\n"); | 152 | printk(KERN_INFO "(teles_cs: looks like the 96 model)\n"); |
| 156 | p_dev->resource[0]->start = cf->io.win[0].base; | ||
| 157 | if (!pcmcia_request_io(p_dev)) | 153 | if (!pcmcia_request_io(p_dev)) |
| 158 | return 0; | 154 | return 0; |
| 159 | } else { | 155 | } else { |
diff --git a/drivers/net/pcmcia/axnet_cs.c b/drivers/net/pcmcia/axnet_cs.c index 17f1040e255e..9d9d997f2e59 100644 --- a/drivers/net/pcmcia/axnet_cs.c +++ b/drivers/net/pcmcia/axnet_cs.c | |||
| @@ -284,34 +284,16 @@ static int try_io_port(struct pcmcia_device *link) | |||
| 284 | } | 284 | } |
| 285 | } | 285 | } |
| 286 | 286 | ||
| 287 | static int axnet_configcheck(struct pcmcia_device *p_dev, | 287 | static int axnet_configcheck(struct pcmcia_device *p_dev, void *priv_data) |
| 288 | cistpl_cftable_entry_t *cfg, | ||
| 289 | cistpl_cftable_entry_t *dflt, | ||
| 290 | void *priv_data) | ||
| 291 | { | 288 | { |
| 292 | int i; | 289 | if (p_dev->config_index == 0) |
| 293 | cistpl_io_t *io = &cfg->io; | 290 | return -EINVAL; |
| 294 | |||
| 295 | if (cfg->index == 0 || cfg->io.nwin == 0) | ||
| 296 | return -ENODEV; | ||
| 297 | 291 | ||
| 298 | p_dev->config_index = 0x05; | 292 | p_dev->config_index = 0x05; |
| 299 | /* For multifunction cards, by convention, we configure the | 293 | if (p_dev->resource[0]->end + p_dev->resource[1]->end < 32) |
| 300 | network function with window 0, and serial with window 1 */ | 294 | return -ENODEV; |
| 301 | if (io->nwin > 1) { | ||
| 302 | i = (io->win[1].len > io->win[0].len); | ||
| 303 | p_dev->resource[1]->start = io->win[1-i].base; | ||
| 304 | p_dev->resource[1]->end = io->win[1-i].len; | ||
| 305 | } else { | ||
| 306 | i = p_dev->resource[1]->end = 0; | ||
| 307 | } | ||
| 308 | p_dev->resource[0]->start = io->win[i].base; | ||
| 309 | p_dev->resource[0]->end = io->win[i].len; | ||
| 310 | p_dev->io_lines = io->flags & CISTPL_IO_LINES_MASK; | ||
| 311 | if (p_dev->resource[0]->end + p_dev->resource[1]->end >= 32) | ||
| 312 | return try_io_port(p_dev); | ||
| 313 | 295 | ||
| 314 | return -ENODEV; | 296 | return try_io_port(p_dev); |
| 315 | } | 297 | } |
| 316 | 298 | ||
| 317 | static int axnet_config(struct pcmcia_device *link) | 299 | static int axnet_config(struct pcmcia_device *link) |
| @@ -324,6 +306,7 @@ static int axnet_config(struct pcmcia_device *link) | |||
| 324 | 306 | ||
| 325 | /* don't trust the CIS on this; Linksys got it wrong */ | 307 | /* don't trust the CIS on this; Linksys got it wrong */ |
| 326 | link->config_regs = 0x63; | 308 | link->config_regs = 0x63; |
| 309 | link->config_flags |= CONF_ENABLE_IRQ | CONF_AUTO_SET_IO; | ||
| 327 | ret = pcmcia_loop_config(link, axnet_configcheck, NULL); | 310 | ret = pcmcia_loop_config(link, axnet_configcheck, NULL); |
| 328 | if (ret != 0) | 311 | if (ret != 0) |
| 329 | goto failed; | 312 | goto failed; |
| @@ -331,7 +314,6 @@ static int axnet_config(struct pcmcia_device *link) | |||
| 331 | if (!link->irq) | 314 | if (!link->irq) |
| 332 | goto failed; | 315 | goto failed; |
| 333 | 316 | ||
| 334 | link->config_flags |= CONF_ENABLE_IRQ; | ||
| 335 | if (resource_size(link->resource[1]) == 8) | 317 | if (resource_size(link->resource[1]) == 8) |
| 336 | link->config_flags |= CONF_ENABLE_SPKR; | 318 | link->config_flags |= CONF_ENABLE_SPKR; |
| 337 | 319 | ||
diff --git a/drivers/net/pcmcia/fmvj18x_cs.c b/drivers/net/pcmcia/fmvj18x_cs.c index c1479e3bfab4..792ab38d979c 100644 --- a/drivers/net/pcmcia/fmvj18x_cs.c +++ b/drivers/net/pcmcia/fmvj18x_cs.c | |||
| @@ -319,10 +319,7 @@ static int ungermann_try_io_port(struct pcmcia_device *link) | |||
| 319 | return ret; /* RequestIO failed */ | 319 | return ret; /* RequestIO failed */ |
| 320 | } | 320 | } |
| 321 | 321 | ||
| 322 | static int fmvj18x_ioprobe(struct pcmcia_device *p_dev, | 322 | static int fmvj18x_ioprobe(struct pcmcia_device *p_dev, void *priv_data) |
| 323 | cistpl_cftable_entry_t *cfg, | ||
| 324 | cistpl_cftable_entry_t *dflt, | ||
| 325 | void *priv_data) | ||
| 326 | { | 323 | { |
| 327 | return 0; /* strange, but that's what the code did already before... */ | 324 | return 0; /* strange, but that's what the code did already before... */ |
| 328 | } | 325 | } |
diff --git a/drivers/net/pcmcia/pcnet_cs.c b/drivers/net/pcmcia/pcnet_cs.c index 12b028c6abc9..ffe2587b9145 100644 --- a/drivers/net/pcmcia/pcnet_cs.c +++ b/drivers/net/pcmcia/pcnet_cs.c | |||
| @@ -259,7 +259,7 @@ static int pcnet_probe(struct pcmcia_device *link) | |||
| 259 | info->p_dev = link; | 259 | info->p_dev = link; |
| 260 | link->priv = dev; | 260 | link->priv = dev; |
| 261 | 261 | ||
| 262 | link->config_flags |= CONF_ENABLE_IRQ; | 262 | link->config_flags |= CONF_ENABLE_IRQ | CONF_AUTO_SET_IO; |
| 263 | 263 | ||
| 264 | dev->netdev_ops = &pcnet_netdev_ops; | 264 | dev->netdev_ops = &pcnet_netdev_ops; |
| 265 | 265 | ||
| @@ -500,42 +500,22 @@ static int try_io_port(struct pcmcia_device *link) | |||
| 500 | } | 500 | } |
| 501 | } | 501 | } |
| 502 | 502 | ||
| 503 | static int pcnet_confcheck(struct pcmcia_device *p_dev, | 503 | static int pcnet_confcheck(struct pcmcia_device *p_dev, void *priv_data) |
| 504 | cistpl_cftable_entry_t *cfg, | ||
| 505 | cistpl_cftable_entry_t *dflt, | ||
| 506 | void *priv_data) | ||
| 507 | { | 504 | { |
| 508 | int *priv = priv_data; | 505 | int *priv = priv_data; |
| 509 | int try = (*priv & 0x1); | 506 | int try = (*priv & 0x1); |
| 510 | int i; | ||
| 511 | cistpl_io_t *io = &cfg->io; | ||
| 512 | 507 | ||
| 513 | if (cfg->index == 0 || cfg->io.nwin == 0) | 508 | *priv &= (p_dev->resource[2]->end >= 0x4000) ? 0x10 : ~0x10; |
| 514 | return -EINVAL; | ||
| 515 | 509 | ||
| 516 | /* For multifunction cards, by convention, we configure the | 510 | if (p_dev->config_index == 0) |
| 517 | network function with window 0, and serial with window 1 */ | 511 | return -EINVAL; |
| 518 | if (io->nwin > 1) { | ||
| 519 | i = (io->win[1].len > io->win[0].len); | ||
| 520 | p_dev->resource[1]->start = io->win[1-i].base; | ||
| 521 | p_dev->resource[1]->end = io->win[1-i].len; | ||
| 522 | } else { | ||
| 523 | i = p_dev->resource[1]->end = 0; | ||
| 524 | } | ||
| 525 | 512 | ||
| 526 | *priv &= ((cfg->mem.nwin == 1) && | 513 | if (p_dev->resource[0]->end + p_dev->resource[1]->end < 32) |
| 527 | (cfg->mem.win[0].len >= 0x4000)) ? 0x10 : ~0x10; | 514 | return -EINVAL; |
| 528 | 515 | ||
| 529 | p_dev->resource[0]->start = io->win[i].base; | 516 | if (try) |
| 530 | p_dev->resource[0]->end = io->win[i].len; | ||
| 531 | if (!try) | ||
| 532 | p_dev->io_lines = io->flags & CISTPL_IO_LINES_MASK; | ||
| 533 | else | ||
| 534 | p_dev->io_lines = 16; | 517 | p_dev->io_lines = 16; |
| 535 | if (p_dev->resource[0]->end + p_dev->resource[1]->end >= 32) | 518 | return try_io_port(p_dev); |
| 536 | return try_io_port(p_dev); | ||
| 537 | |||
| 538 | return -EINVAL; | ||
| 539 | } | 519 | } |
| 540 | 520 | ||
| 541 | static hw_info_t *pcnet_try_config(struct pcmcia_device *link, | 521 | static hw_info_t *pcnet_try_config(struct pcmcia_device *link, |
diff --git a/drivers/net/pcmcia/smc91c92_cs.c b/drivers/net/pcmcia/smc91c92_cs.c index e127d2b546dd..a8cef28507de 100644 --- a/drivers/net/pcmcia/smc91c92_cs.c +++ b/drivers/net/pcmcia/smc91c92_cs.c | |||
| @@ -323,9 +323,6 @@ static int smc91c92_probe(struct pcmcia_device *link) | |||
| 323 | link->priv = dev; | 323 | link->priv = dev; |
| 324 | 324 | ||
| 325 | spin_lock_init(&smc->lock); | 325 | spin_lock_init(&smc->lock); |
| 326 | link->resource[0]->end = 16; | ||
| 327 | link->resource[0]->flags |= IO_DATA_PATH_WIDTH_AUTO; | ||
| 328 | link->config_flags |= CONF_ENABLE_IRQ; | ||
| 329 | 326 | ||
| 330 | /* The SMC91c92-specific entries in the device structure. */ | 327 | /* The SMC91c92-specific entries in the device structure. */ |
| 331 | dev->netdev_ops = &smc_netdev_ops; | 328 | dev->netdev_ops = &smc_netdev_ops; |
| @@ -417,18 +414,21 @@ static int mhz_3288_power(struct pcmcia_device *link) | |||
| 417 | return 0; | 414 | return 0; |
| 418 | } | 415 | } |
| 419 | 416 | ||
| 420 | static int mhz_mfc_config_check(struct pcmcia_device *p_dev, | 417 | static int mhz_mfc_config_check(struct pcmcia_device *p_dev, void *priv_data) |
| 421 | cistpl_cftable_entry_t *cf, | ||
| 422 | cistpl_cftable_entry_t *dflt, | ||
| 423 | void *priv_data) | ||
| 424 | { | 418 | { |
| 425 | int k; | 419 | int k; |
| 426 | p_dev->resource[1]->start = cf->io.win[0].base; | 420 | p_dev->io_lines = 16; |
| 421 | p_dev->resource[1]->start = p_dev->resource[0]->start; | ||
| 422 | p_dev->resource[1]->end = 8; | ||
| 423 | p_dev->resource[1]->flags &= ~IO_DATA_PATH_WIDTH; | ||
| 424 | p_dev->resource[1]->flags |= IO_DATA_PATH_WIDTH_8; | ||
| 425 | p_dev->resource[0]->end = 16; | ||
| 426 | p_dev->resource[0]->flags &= ~IO_DATA_PATH_WIDTH; | ||
| 427 | p_dev->resource[0]->flags |= IO_DATA_PATH_WIDTH_AUTO; | ||
| 427 | for (k = 0; k < 0x400; k += 0x10) { | 428 | for (k = 0; k < 0x400; k += 0x10) { |
| 428 | if (k & 0x80) | 429 | if (k & 0x80) |
| 429 | continue; | 430 | continue; |
| 430 | p_dev->resource[0]->start = k ^ 0x300; | 431 | p_dev->resource[0]->start = k ^ 0x300; |
| 431 | p_dev->io_lines = 16; | ||
| 432 | if (!pcmcia_request_io(p_dev)) | 432 | if (!pcmcia_request_io(p_dev)) |
| 433 | return 0; | 433 | return 0; |
| 434 | } | 434 | } |
| @@ -442,9 +442,8 @@ static int mhz_mfc_config(struct pcmcia_device *link) | |||
| 442 | unsigned int offset; | 442 | unsigned int offset; |
| 443 | int i; | 443 | int i; |
| 444 | 444 | ||
| 445 | link->config_flags |= CONF_ENABLE_SPKR; | 445 | link->config_flags |= CONF_ENABLE_SPKR | CONF_ENABLE_IRQ | |
| 446 | link->resource[1]->flags |= IO_DATA_PATH_WIDTH_8; | 446 | CONF_AUTO_SET_IO; |
| 447 | link->resource[1]->end = 8; | ||
| 448 | 447 | ||
| 449 | /* The Megahertz combo cards have modem-like CIS entries, so | 448 | /* The Megahertz combo cards have modem-like CIS entries, so |
| 450 | we have to explicitly try a bunch of port combinations. */ | 449 | we have to explicitly try a bunch of port combinations. */ |
| @@ -586,13 +585,12 @@ static int mot_setup(struct pcmcia_device *link) | |||
| 586 | 585 | ||
| 587 | /*====================================================================*/ | 586 | /*====================================================================*/ |
| 588 | 587 | ||
| 589 | static int smc_configcheck(struct pcmcia_device *p_dev, | 588 | static int smc_configcheck(struct pcmcia_device *p_dev, void *priv_data) |
| 590 | cistpl_cftable_entry_t *cf, | ||
| 591 | cistpl_cftable_entry_t *dflt, | ||
| 592 | void *priv_data) | ||
| 593 | { | 589 | { |
| 594 | p_dev->resource[0]->start = cf->io.win[0].base; | 590 | p_dev->resource[0]->end = 16; |
| 595 | p_dev->io_lines = cf->io.flags & CISTPL_IO_LINES_MASK; | 591 | p_dev->resource[0]->flags &= ~IO_DATA_PATH_WIDTH; |
| 592 | p_dev->resource[0]->flags |= IO_DATA_PATH_WIDTH_AUTO; | ||
| 593 | |||
| 596 | return pcmcia_request_io(p_dev); | 594 | return pcmcia_request_io(p_dev); |
| 597 | } | 595 | } |
| 598 | 596 | ||
| @@ -601,7 +599,8 @@ static int smc_config(struct pcmcia_device *link) | |||
| 601 | struct net_device *dev = link->priv; | 599 | struct net_device *dev = link->priv; |
| 602 | int i; | 600 | int i; |
| 603 | 601 | ||
| 604 | link->resource[0]->end = 16; | 602 | link->config_flags |= CONF_ENABLE_IRQ | CONF_AUTO_SET_IO; |
| 603 | |||
| 605 | i = pcmcia_loop_config(link, smc_configcheck, NULL); | 604 | i = pcmcia_loop_config(link, smc_configcheck, NULL); |
| 606 | if (!i) | 605 | if (!i) |
| 607 | dev->base_addr = link->resource[0]->start; | 606 | dev->base_addr = link->resource[0]->start; |
| @@ -634,7 +633,7 @@ static int osi_config(struct pcmcia_device *link) | |||
| 634 | static const unsigned int com[4] = { 0x3f8, 0x2f8, 0x3e8, 0x2e8 }; | 633 | static const unsigned int com[4] = { 0x3f8, 0x2f8, 0x3e8, 0x2e8 }; |
| 635 | int i, j; | 634 | int i, j; |
| 636 | 635 | ||
| 637 | link->config_flags |= CONF_ENABLE_SPKR; | 636 | link->config_flags |= CONF_ENABLE_SPKR | CONF_ENABLE_IRQ; |
| 638 | link->resource[0]->end = 64; | 637 | link->resource[0]->end = 64; |
| 639 | link->resource[1]->flags |= IO_DATA_PATH_WIDTH_8; | 638 | link->resource[1]->flags |= IO_DATA_PATH_WIDTH_8; |
| 640 | link->resource[1]->end = 8; | 639 | link->resource[1]->end = 8; |
diff --git a/drivers/net/pcmcia/xirc2ps_cs.c b/drivers/net/pcmcia/xirc2ps_cs.c index 2bc2eb89c4cd..cecc07454e9e 100644 --- a/drivers/net/pcmcia/xirc2ps_cs.c +++ b/drivers/net/pcmcia/xirc2ps_cs.c | |||
| @@ -528,7 +528,6 @@ xirc2ps_probe(struct pcmcia_device *link) | |||
| 528 | link->priv = dev; | 528 | link->priv = dev; |
| 529 | 529 | ||
| 530 | /* General socket configuration */ | 530 | /* General socket configuration */ |
| 531 | link->config_flags |= CONF_ENABLE_IRQ; | ||
| 532 | link->config_index = 1; | 531 | link->config_index = 1; |
| 533 | 532 | ||
| 534 | /* Fill in card specific entries */ | 533 | /* Fill in card specific entries */ |
| @@ -665,42 +664,53 @@ has_ce2_string(struct pcmcia_device * p_dev) | |||
| 665 | } | 664 | } |
| 666 | 665 | ||
| 667 | static int | 666 | static int |
| 668 | xirc2ps_config_modem(struct pcmcia_device *p_dev, | 667 | xirc2ps_config_modem(struct pcmcia_device *p_dev, void *priv_data) |
| 669 | cistpl_cftable_entry_t *cf, | ||
| 670 | cistpl_cftable_entry_t *dflt, | ||
| 671 | void *priv_data) | ||
| 672 | { | 668 | { |
| 673 | unsigned int ioaddr; | 669 | unsigned int ioaddr; |
| 674 | 670 | ||
| 675 | if (cf->io.nwin > 0 && (cf->io.win[0].base & 0xf) == 8) { | 671 | if ((p_dev->resource[0]->start & 0xf) == 8) |
| 676 | for (ioaddr = 0x300; ioaddr < 0x400; ioaddr += 0x10) { | 672 | return -ENODEV; |
| 677 | p_dev->resource[1]->start = cf->io.win[0].base; | 673 | |
| 678 | p_dev->resource[0]->start = ioaddr; | 674 | p_dev->resource[0]->end = 16; |
| 679 | if (!pcmcia_request_io(p_dev)) | 675 | p_dev->resource[1]->end = 8; |
| 680 | return 0; | 676 | p_dev->resource[0]->flags &= ~IO_DATA_PATH_WIDTH; |
| 681 | } | 677 | p_dev->resource[0]->flags |= IO_DATA_PATH_WIDTH_16; |
| 678 | p_dev->resource[1]->flags &= ~IO_DATA_PATH_WIDTH; | ||
| 679 | p_dev->resource[1]->flags |= IO_DATA_PATH_WIDTH_8; | ||
| 680 | p_dev->io_lines = 10; | ||
| 681 | |||
| 682 | p_dev->resource[1]->start = p_dev->resource[0]->start; | ||
| 683 | for (ioaddr = 0x300; ioaddr < 0x400; ioaddr += 0x10) { | ||
| 684 | p_dev->resource[0]->start = ioaddr; | ||
| 685 | if (!pcmcia_request_io(p_dev)) | ||
| 686 | return 0; | ||
| 682 | } | 687 | } |
| 683 | return -ENODEV; | 688 | return -ENODEV; |
| 684 | } | 689 | } |
| 685 | 690 | ||
| 686 | static int | 691 | static int |
| 687 | xirc2ps_config_check(struct pcmcia_device *p_dev, | 692 | xirc2ps_config_check(struct pcmcia_device *p_dev, void *priv_data) |
| 688 | cistpl_cftable_entry_t *cf, | ||
| 689 | cistpl_cftable_entry_t *dflt, | ||
| 690 | void *priv_data) | ||
| 691 | { | 693 | { |
| 692 | int *pass = priv_data; | 694 | int *pass = priv_data; |
| 695 | resource_size_t tmp = p_dev->resource[1]->start; | ||
| 693 | 696 | ||
| 694 | if (cf->io.nwin > 0 && (cf->io.win[0].base & 0xf) == 8) { | 697 | tmp += (*pass ? (p_dev->config_index & 0x20 ? -24 : 8) |
| 695 | p_dev->resource[1]->start = cf->io.win[0].base; | 698 | : (p_dev->config_index & 0x20 ? 8 : -24)); |
| 696 | p_dev->resource[0]->start = p_dev->resource[1]->start | 699 | |
| 697 | + (*pass ? (cf->index & 0x20 ? -24:8) | 700 | if ((p_dev->resource[0]->start & 0xf) == 8) |
| 698 | : (cf->index & 0x20 ? 8:-24)); | 701 | return -ENODEV; |
| 699 | if (!pcmcia_request_io(p_dev)) | 702 | |
| 700 | return 0; | 703 | p_dev->resource[0]->end = 18; |
| 701 | } | 704 | p_dev->resource[1]->end = 8; |
| 702 | return -ENODEV; | 705 | p_dev->resource[0]->flags &= ~IO_DATA_PATH_WIDTH; |
| 706 | p_dev->resource[0]->flags |= IO_DATA_PATH_WIDTH_16; | ||
| 707 | p_dev->resource[1]->flags &= ~IO_DATA_PATH_WIDTH; | ||
| 708 | p_dev->resource[1]->flags |= IO_DATA_PATH_WIDTH_8; | ||
| 709 | p_dev->io_lines = 10; | ||
| 703 | 710 | ||
| 711 | p_dev->resource[1]->start = p_dev->resource[0]->start; | ||
| 712 | p_dev->resource[0]->start = tmp; | ||
| 713 | return pcmcia_request_io(p_dev); | ||
| 704 | } | 714 | } |
| 705 | 715 | ||
| 706 | 716 | ||
| @@ -803,21 +813,16 @@ xirc2ps_config(struct pcmcia_device * link) | |||
| 803 | goto failure; | 813 | goto failure; |
| 804 | } | 814 | } |
| 805 | 815 | ||
| 806 | link->resource[0]->flags |= IO_DATA_PATH_WIDTH_16; | ||
| 807 | link->io_lines = 10; | ||
| 808 | if (local->modem) { | 816 | if (local->modem) { |
| 809 | int pass; | 817 | int pass; |
| 818 | link->config_flags |= CONF_AUTO_SET_IO; | ||
| 810 | 819 | ||
| 811 | link->resource[1]->end = 8; | ||
| 812 | link->resource[1]->flags |= IO_DATA_PATH_WIDTH_8; | ||
| 813 | if (local->dingo) { | 820 | if (local->dingo) { |
| 814 | /* Take the Modem IO port from the CIS and scan for a free | 821 | /* Take the Modem IO port from the CIS and scan for a free |
| 815 | * Ethernet port */ | 822 | * Ethernet port */ |
| 816 | link->resource[0]->end = 16; /* no Mako stuff anymore */ | ||
| 817 | if (!pcmcia_loop_config(link, xirc2ps_config_modem, NULL)) | 823 | if (!pcmcia_loop_config(link, xirc2ps_config_modem, NULL)) |
| 818 | goto port_found; | 824 | goto port_found; |
| 819 | } else { | 825 | } else { |
| 820 | link->resource[0]->end = 18; | ||
| 821 | /* We do 2 passes here: The first one uses the regular mapping and | 826 | /* We do 2 passes here: The first one uses the regular mapping and |
| 822 | * the second tries again, thereby considering that the 32 ports are | 827 | * the second tries again, thereby considering that the 32 ports are |
| 823 | * mirrored every 32 bytes. Actually we use a mirrored port for | 828 | * mirrored every 32 bytes. Actually we use a mirrored port for |
| @@ -833,7 +838,9 @@ xirc2ps_config(struct pcmcia_device * link) | |||
| 833 | } | 838 | } |
| 834 | printk(KNOT_XIRC "no ports available\n"); | 839 | printk(KNOT_XIRC "no ports available\n"); |
| 835 | } else { | 840 | } else { |
| 841 | link->io_lines = 10; | ||
| 836 | link->resource[0]->end = 16; | 842 | link->resource[0]->end = 16; |
| 843 | link->resource[0]->flags |= IO_DATA_PATH_WIDTH_16; | ||
| 837 | for (ioaddr = 0x300; ioaddr < 0x400; ioaddr += 0x10) { | 844 | for (ioaddr = 0x300; ioaddr < 0x400; ioaddr += 0x10) { |
| 838 | link->resource[0]->start = ioaddr; | 845 | link->resource[0]->start = ioaddr; |
| 839 | if (!(err = pcmcia_request_io(link))) | 846 | if (!(err = pcmcia_request_io(link))) |
diff --git a/drivers/net/wireless/airo_cs.c b/drivers/net/wireless/airo_cs.c index 63bf662e9c7f..77682f27772b 100644 --- a/drivers/net/wireless/airo_cs.c +++ b/drivers/net/wireless/airo_cs.c | |||
| @@ -137,36 +137,12 @@ static void airo_detach(struct pcmcia_device *link) | |||
| 137 | 137 | ||
| 138 | ======================================================================*/ | 138 | ======================================================================*/ |
| 139 | 139 | ||
| 140 | static int airo_cs_config_check(struct pcmcia_device *p_dev, | 140 | static int airo_cs_config_check(struct pcmcia_device *p_dev, void *priv_data) |
| 141 | cistpl_cftable_entry_t *cfg, | ||
| 142 | cistpl_cftable_entry_t *dflt, | ||
| 143 | void *priv_data) | ||
| 144 | { | 141 | { |
| 145 | if (cfg->index == 0) | 142 | if (p_dev->config_index == 0) |
| 146 | return -ENODEV; | 143 | return -EINVAL; |
| 147 | |||
| 148 | /* IO window settings */ | ||
| 149 | p_dev->resource[0]->end = p_dev->resource[1]->end = 0; | ||
| 150 | if ((cfg->io.nwin > 0) || (dflt->io.nwin > 0)) { | ||
| 151 | cistpl_io_t *io = (cfg->io.nwin) ? &cfg->io : &dflt->io; | ||
| 152 | p_dev->resource[0]->flags &= ~IO_DATA_PATH_WIDTH; | ||
| 153 | p_dev->resource[0]->flags |= | ||
| 154 | pcmcia_io_cfg_data_width(io->flags); | ||
| 155 | p_dev->resource[0]->start = io->win[0].base; | ||
| 156 | p_dev->resource[0]->end = io->win[0].len; | ||
| 157 | if (io->nwin > 1) { | ||
| 158 | p_dev->resource[1]->flags = p_dev->resource[0]->flags; | ||
| 159 | p_dev->resource[1]->start = io->win[1].base; | ||
| 160 | p_dev->resource[1]->end = io->win[1].len; | ||
| 161 | } | ||
| 162 | } | ||
| 163 | |||
| 164 | /* This reserves IO space but doesn't actually enable it */ | ||
| 165 | if (pcmcia_request_io(p_dev) != 0) | ||
| 166 | return -ENODEV; | ||
| 167 | 144 | ||
| 168 | /* If we got this far, we're cool! */ | 145 | return pcmcia_request_io(p_dev); |
| 169 | return 0; | ||
| 170 | } | 146 | } |
| 171 | 147 | ||
| 172 | 148 | ||
| @@ -180,7 +156,7 @@ static int airo_config(struct pcmcia_device *link) | |||
| 180 | dev_dbg(&link->dev, "airo_config\n"); | 156 | dev_dbg(&link->dev, "airo_config\n"); |
| 181 | 157 | ||
| 182 | link->config_flags |= CONF_ENABLE_IRQ | CONF_AUTO_SET_VPP | | 158 | link->config_flags |= CONF_ENABLE_IRQ | CONF_AUTO_SET_VPP | |
| 183 | CONF_AUTO_AUDIO; | 159 | CONF_AUTO_AUDIO | CONF_AUTO_SET_IO; |
| 184 | 160 | ||
| 185 | /* | 161 | /* |
| 186 | * In this loop, we scan the CIS for configuration table | 162 | * In this loop, we scan the CIS for configuration table |
diff --git a/drivers/net/wireless/atmel_cs.c b/drivers/net/wireless/atmel_cs.c index 812decd3fbe9..202938022112 100644 --- a/drivers/net/wireless/atmel_cs.c +++ b/drivers/net/wireless/atmel_cs.c | |||
| @@ -154,31 +154,11 @@ static int card_present(void *arg) | |||
| 154 | return 0; | 154 | return 0; |
| 155 | } | 155 | } |
| 156 | 156 | ||
| 157 | static int atmel_config_check(struct pcmcia_device *p_dev, | 157 | static int atmel_config_check(struct pcmcia_device *p_dev, void *priv_data) |
| 158 | cistpl_cftable_entry_t *cfg, | ||
| 159 | cistpl_cftable_entry_t *dflt, | ||
| 160 | void *priv_data) | ||
| 161 | { | 158 | { |
| 162 | if (cfg->index == 0) | 159 | if (p_dev->config_index == 0) |
| 163 | return -ENODEV; | 160 | return -EINVAL; |
| 164 | |||
| 165 | /* IO window settings */ | ||
| 166 | p_dev->resource[0]->end = p_dev->resource[1]->end = 0; | ||
| 167 | if ((cfg->io.nwin > 0) || (dflt->io.nwin > 0)) { | ||
| 168 | cistpl_io_t *io = (cfg->io.nwin) ? &cfg->io : &dflt->io; | ||
| 169 | p_dev->resource[0]->flags &= ~IO_DATA_PATH_WIDTH; | ||
| 170 | p_dev->resource[0]->flags |= | ||
| 171 | pcmcia_io_cfg_data_width(io->flags); | ||
| 172 | p_dev->resource[0]->start = io->win[0].base; | ||
| 173 | p_dev->resource[0]->end = io->win[0].len; | ||
| 174 | if (io->nwin > 1) { | ||
| 175 | p_dev->resource[1]->flags = p_dev->resource[0]->flags; | ||
| 176 | p_dev->resource[1]->start = io->win[1].base; | ||
| 177 | p_dev->resource[1]->end = io->win[1].len; | ||
| 178 | } | ||
| 179 | } | ||
| 180 | 161 | ||
| 181 | /* This reserves IO space but doesn't actually enable it */ | ||
| 182 | return pcmcia_request_io(p_dev); | 162 | return pcmcia_request_io(p_dev); |
| 183 | } | 163 | } |
| 184 | 164 | ||
| @@ -194,7 +174,7 @@ static int atmel_config(struct pcmcia_device *link) | |||
| 194 | dev_dbg(&link->dev, "atmel_config\n"); | 174 | dev_dbg(&link->dev, "atmel_config\n"); |
| 195 | 175 | ||
| 196 | link->config_flags |= CONF_ENABLE_IRQ | CONF_AUTO_SET_VPP | | 176 | link->config_flags |= CONF_ENABLE_IRQ | CONF_AUTO_SET_VPP | |
| 197 | CONF_AUTO_AUDIO; | 177 | CONF_AUTO_AUDIO | CONF_AUTO_SET_IO; |
| 198 | 178 | ||
| 199 | /* | 179 | /* |
| 200 | In this loop, we scan the CIS for configuration table entries, | 180 | In this loop, we scan the CIS for configuration table entries, |
diff --git a/drivers/net/wireless/hostap/hostap_cs.c b/drivers/net/wireless/hostap/hostap_cs.c index d4f19af1757f..e57b20134d39 100644 --- a/drivers/net/wireless/hostap/hostap_cs.c +++ b/drivers/net/wireless/hostap/hostap_cs.c | |||
| @@ -469,46 +469,11 @@ static void prism2_detach(struct pcmcia_device *link) | |||
| 469 | /* run after a CARD_INSERTION event is received to configure the PCMCIA | 469 | /* run after a CARD_INSERTION event is received to configure the PCMCIA |
| 470 | * socket and make the device available to the system */ | 470 | * socket and make the device available to the system */ |
| 471 | 471 | ||
| 472 | static int prism2_config_check(struct pcmcia_device *p_dev, | 472 | static int prism2_config_check(struct pcmcia_device *p_dev, void *priv_data) |
| 473 | cistpl_cftable_entry_t *cfg, | ||
| 474 | cistpl_cftable_entry_t *dflt, | ||
| 475 | void *priv_data) | ||
| 476 | { | 473 | { |
| 477 | if (cfg->index == 0) | 474 | if (p_dev->config_index == 0) |
| 478 | return -ENODEV; | 475 | return -EINVAL; |
| 479 | |||
| 480 | PDEBUG(DEBUG_EXTRA, "Checking CFTABLE_ENTRY 0x%02X " | ||
| 481 | "(default 0x%02X)\n", cfg->index, dflt->index); | ||
| 482 | |||
| 483 | if (cfg->vpp1.present & (1 << CISTPL_POWER_VNOM)) | ||
| 484 | p_dev->vpp = cfg->vpp1.param[CISTPL_POWER_VNOM] / 10000; | ||
| 485 | else if (dflt->vpp1.present & (1 << CISTPL_POWER_VNOM)) | ||
| 486 | p_dev->vpp = dflt->vpp1.param[CISTPL_POWER_VNOM] / 10000; | ||
| 487 | |||
| 488 | /* Do we need to allocate an interrupt? */ | ||
| 489 | p_dev->config_flags |= CONF_ENABLE_IRQ; | ||
| 490 | |||
| 491 | /* IO window settings */ | ||
| 492 | PDEBUG(DEBUG_EXTRA, "IO window settings: cfg->io.nwin=%d " | ||
| 493 | "dflt->io.nwin=%d\n", | ||
| 494 | cfg->io.nwin, dflt->io.nwin); | ||
| 495 | p_dev->resource[0]->end = p_dev->resource[1]->end = 0; | ||
| 496 | if ((cfg->io.nwin > 0) || (dflt->io.nwin > 0)) { | ||
| 497 | cistpl_io_t *io = (cfg->io.nwin) ? &cfg->io : &dflt->io; | ||
| 498 | p_dev->resource[0]->flags &= ~IO_DATA_PATH_WIDTH; | ||
| 499 | p_dev->resource[0]->flags |= | ||
| 500 | pcmcia_io_cfg_data_width(io->flags); | ||
| 501 | p_dev->io_lines = io->flags & CISTPL_IO_LINES_MASK; | ||
| 502 | p_dev->resource[0]->start = io->win[0].base; | ||
| 503 | p_dev->resource[0]->end = io->win[0].len; | ||
| 504 | if (io->nwin > 1) { | ||
| 505 | p_dev->resource[1]->flags = p_dev->resource[0]->flags; | ||
| 506 | p_dev->resource[1]->start = io->win[1].base; | ||
| 507 | p_dev->resource[1]->end = io->win[1].len; | ||
| 508 | } | ||
| 509 | } | ||
| 510 | 476 | ||
| 511 | /* This reserves IO space but doesn't actually enable it */ | ||
| 512 | return pcmcia_request_io(p_dev); | 477 | return pcmcia_request_io(p_dev); |
| 513 | } | 478 | } |
| 514 | 479 | ||
| @@ -531,7 +496,7 @@ static int prism2_config(struct pcmcia_device *link) | |||
| 531 | 496 | ||
| 532 | /* Look for an appropriate configuration table entry in the CIS */ | 497 | /* Look for an appropriate configuration table entry in the CIS */ |
| 533 | link->config_flags |= CONF_AUTO_SET_VPP | CONF_AUTO_AUDIO | | 498 | link->config_flags |= CONF_AUTO_SET_VPP | CONF_AUTO_AUDIO | |
| 534 | CONF_AUTO_CHECK_VCC; | 499 | CONF_AUTO_CHECK_VCC | CONF_AUTO_SET_IO | CONF_ENABLE_IRQ; |
| 535 | if (ignore_cis_vcc) | 500 | if (ignore_cis_vcc) |
| 536 | link->config_flags &= ~CONF_AUTO_CHECK_VCC; | 501 | link->config_flags &= ~CONF_AUTO_CHECK_VCC; |
| 537 | ret = pcmcia_loop_config(link, prism2_config_check, NULL); | 502 | ret = pcmcia_loop_config(link, prism2_config_check, NULL); |
diff --git a/drivers/net/wireless/libertas/if_cs.c b/drivers/net/wireless/libertas/if_cs.c index 031f3e6da3c9..2c6f28ac5197 100644 --- a/drivers/net/wireless/libertas/if_cs.c +++ b/drivers/net/wireless/libertas/if_cs.c | |||
| @@ -794,20 +794,12 @@ static void if_cs_release(struct pcmcia_device *p_dev) | |||
| 794 | * insertion event. | 794 | * insertion event. |
| 795 | */ | 795 | */ |
| 796 | 796 | ||
| 797 | static int if_cs_ioprobe(struct pcmcia_device *p_dev, | 797 | static int if_cs_ioprobe(struct pcmcia_device *p_dev, void *priv_data) |
| 798 | cistpl_cftable_entry_t *cfg, | ||
| 799 | cistpl_cftable_entry_t *dflt, | ||
| 800 | void *priv_data) | ||
| 801 | { | 798 | { |
| 799 | p_dev->resource[0]->flags &= ~IO_DATA_PATH_WIDTH; | ||
| 802 | p_dev->resource[0]->flags |= IO_DATA_PATH_WIDTH_AUTO; | 800 | p_dev->resource[0]->flags |= IO_DATA_PATH_WIDTH_AUTO; |
| 803 | p_dev->resource[0]->start = cfg->io.win[0].base; | ||
| 804 | p_dev->resource[0]->end = cfg->io.win[0].len; | ||
| 805 | 801 | ||
| 806 | /* Do we need to allocate an interrupt? */ | 802 | if (p_dev->resource[1]->end) { |
| 807 | p_dev->config_flags |= CONF_ENABLE_IRQ; | ||
| 808 | |||
| 809 | /* IO window settings */ | ||
| 810 | if (cfg->io.nwin != 1) { | ||
| 811 | lbs_pr_err("wrong CIS (check number of IO windows)\n"); | 803 | lbs_pr_err("wrong CIS (check number of IO windows)\n"); |
| 812 | return -ENODEV; | 804 | return -ENODEV; |
| 813 | } | 805 | } |
| @@ -833,6 +825,8 @@ static int if_cs_probe(struct pcmcia_device *p_dev) | |||
| 833 | card->p_dev = p_dev; | 825 | card->p_dev = p_dev; |
| 834 | p_dev->priv = card; | 826 | p_dev->priv = card; |
| 835 | 827 | ||
| 828 | p_dev->config_flags |= CONF_ENABLE_IRQ | CONF_AUTO_SET_IO; | ||
| 829 | |||
| 836 | if (pcmcia_loop_config(p_dev, if_cs_ioprobe, NULL)) { | 830 | if (pcmcia_loop_config(p_dev, if_cs_ioprobe, NULL)) { |
| 837 | lbs_pr_err("error in pcmcia_loop_config\n"); | 831 | lbs_pr_err("error in pcmcia_loop_config\n"); |
| 838 | goto out1; | 832 | goto out1; |
diff --git a/drivers/net/wireless/orinoco/orinoco_cs.c b/drivers/net/wireless/orinoco/orinoco_cs.c index b92173827b55..263dfe9e0e30 100644 --- a/drivers/net/wireless/orinoco/orinoco_cs.c +++ b/drivers/net/wireless/orinoco/orinoco_cs.c | |||
| @@ -142,42 +142,12 @@ static void orinoco_cs_detach(struct pcmcia_device *link) | |||
| 142 | * device available to the system. | 142 | * device available to the system. |
| 143 | */ | 143 | */ |
| 144 | 144 | ||
| 145 | static int orinoco_cs_config_check(struct pcmcia_device *p_dev, | 145 | static int orinoco_cs_config_check(struct pcmcia_device *p_dev, void *priv_data) |
| 146 | cistpl_cftable_entry_t *cfg, | ||
| 147 | cistpl_cftable_entry_t *dflt, | ||
| 148 | void *priv_data) | ||
| 149 | { | 146 | { |
| 150 | if (cfg->index == 0) | 147 | if (p_dev->config_index == 0) |
| 151 | goto next_entry; | 148 | return -EINVAL; |
| 152 | |||
| 153 | /* Do we need to allocate an interrupt? */ | ||
| 154 | p_dev->config_flags |= CONF_ENABLE_IRQ; | ||
| 155 | |||
| 156 | /* IO window settings */ | ||
| 157 | p_dev->resource[0]->end = p_dev->resource[1]->end = 0; | ||
| 158 | if ((cfg->io.nwin > 0) || (dflt->io.nwin > 0)) { | ||
| 159 | cistpl_io_t *io = (cfg->io.nwin) ? &cfg->io : &dflt->io; | ||
| 160 | p_dev->io_lines = io->flags & CISTPL_IO_LINES_MASK; | ||
| 161 | p_dev->resource[0]->flags &= ~IO_DATA_PATH_WIDTH; | ||
| 162 | p_dev->resource[0]->flags |= | ||
| 163 | pcmcia_io_cfg_data_width(io->flags); | ||
| 164 | p_dev->resource[0]->start = io->win[0].base; | ||
| 165 | p_dev->resource[0]->end = io->win[0].len; | ||
| 166 | if (io->nwin > 1) { | ||
| 167 | p_dev->resource[1]->flags = p_dev->resource[0]->flags; | ||
| 168 | p_dev->resource[1]->start = io->win[1].base; | ||
| 169 | p_dev->resource[1]->end = io->win[1].len; | ||
| 170 | } | ||
| 171 | |||
| 172 | /* This reserves IO space but doesn't actually enable it */ | ||
| 173 | if (pcmcia_request_io(p_dev) != 0) | ||
| 174 | goto next_entry; | ||
| 175 | } | ||
| 176 | return 0; | ||
| 177 | 149 | ||
| 178 | next_entry: | 150 | return pcmcia_request_io(p_dev); |
| 179 | pcmcia_disable_device(p_dev); | ||
| 180 | return -ENODEV; | ||
| 181 | }; | 151 | }; |
| 182 | 152 | ||
| 183 | static int | 153 | static int |
| @@ -202,7 +172,8 @@ orinoco_cs_config(struct pcmcia_device *link) | |||
| 202 | * and most client drivers will only use the CIS to fill in | 172 | * and most client drivers will only use the CIS to fill in |
| 203 | * implementation-defined details. | 173 | * implementation-defined details. |
| 204 | */ | 174 | */ |
| 205 | link->config_flags |= CONF_AUTO_SET_VPP | CONF_AUTO_CHECK_VCC; | 175 | link->config_flags |= CONF_AUTO_SET_VPP | CONF_AUTO_CHECK_VCC | |
| 176 | CONF_AUTO_SET_IO | CONF_ENABLE_IRQ; | ||
| 206 | if (ignore_cis_vcc) | 177 | if (ignore_cis_vcc) |
| 207 | link->config_flags &= ~CONF_AUTO_CHECK_VCC; | 178 | link->config_flags &= ~CONF_AUTO_CHECK_VCC; |
| 208 | ret = pcmcia_loop_config(link, orinoco_cs_config_check, NULL); | 179 | ret = pcmcia_loop_config(link, orinoco_cs_config_check, NULL); |
diff --git a/drivers/net/wireless/orinoco/spectrum_cs.c b/drivers/net/wireless/orinoco/spectrum_cs.c index f462c78856e9..78446507873f 100644 --- a/drivers/net/wireless/orinoco/spectrum_cs.c +++ b/drivers/net/wireless/orinoco/spectrum_cs.c | |||
| @@ -205,48 +205,12 @@ static void spectrum_cs_detach(struct pcmcia_device *link) | |||
| 205 | */ | 205 | */ |
| 206 | 206 | ||
| 207 | static int spectrum_cs_config_check(struct pcmcia_device *p_dev, | 207 | static int spectrum_cs_config_check(struct pcmcia_device *p_dev, |
| 208 | cistpl_cftable_entry_t *cfg, | ||
| 209 | cistpl_cftable_entry_t *dflt, | ||
| 210 | void *priv_data) | 208 | void *priv_data) |
| 211 | { | 209 | { |
| 212 | if (cfg->index == 0) | 210 | if (p_dev->config_index == 0) |
| 213 | goto next_entry; | 211 | return -EINVAL; |
| 214 | |||
| 215 | if (cfg->vpp1.present & (1 << CISTPL_POWER_VNOM)) | ||
| 216 | p_dev->vpp = | ||
| 217 | cfg->vpp1.param[CISTPL_POWER_VNOM] / 10000; | ||
| 218 | else if (dflt->vpp1.present & (1 << CISTPL_POWER_VNOM)) | ||
| 219 | p_dev->vpp = | ||
| 220 | dflt->vpp1.param[CISTPL_POWER_VNOM] / 10000; | ||
| 221 | |||
| 222 | /* Do we need to allocate an interrupt? */ | ||
| 223 | p_dev->config_flags |= CONF_ENABLE_IRQ; | ||
| 224 | |||
| 225 | /* IO window settings */ | ||
| 226 | p_dev->resource[0]->end = p_dev->resource[1]->end = 0; | ||
| 227 | if ((cfg->io.nwin > 0) || (dflt->io.nwin > 0)) { | ||
| 228 | cistpl_io_t *io = (cfg->io.nwin) ? &cfg->io : &dflt->io; | ||
| 229 | p_dev->io_lines = io->flags & CISTPL_IO_LINES_MASK; | ||
| 230 | p_dev->resource[0]->flags &= ~IO_DATA_PATH_WIDTH; | ||
| 231 | p_dev->resource[0]->flags |= | ||
| 232 | pcmcia_io_cfg_data_width(io->flags); | ||
| 233 | p_dev->resource[0]->start = io->win[0].base; | ||
| 234 | p_dev->resource[0]->end = io->win[0].len; | ||
| 235 | if (io->nwin > 1) { | ||
| 236 | p_dev->resource[1]->flags = p_dev->resource[0]->flags; | ||
| 237 | p_dev->resource[1]->start = io->win[1].base; | ||
| 238 | p_dev->resource[1]->end = io->win[1].len; | ||
| 239 | } | ||
| 240 | |||
| 241 | /* This reserves IO space but doesn't actually enable it */ | ||
| 242 | if (pcmcia_request_io(p_dev) != 0) | ||
| 243 | goto next_entry; | ||
| 244 | } | ||
| 245 | return 0; | ||
| 246 | 212 | ||
| 247 | next_entry: | 213 | return pcmcia_request_io(p_dev); |
| 248 | pcmcia_disable_device(p_dev); | ||
| 249 | return -ENODEV; | ||
| 250 | }; | 214 | }; |
| 251 | 215 | ||
| 252 | static int | 216 | static int |
| @@ -271,7 +235,8 @@ spectrum_cs_config(struct pcmcia_device *link) | |||
| 271 | * and most client drivers will only use the CIS to fill in | 235 | * and most client drivers will only use the CIS to fill in |
| 272 | * implementation-defined details. | 236 | * implementation-defined details. |
| 273 | */ | 237 | */ |
| 274 | link->config_flags |= CONF_AUTO_SET_VPP | CONF_AUTO_CHECK_VCC; | 238 | link->config_flags |= CONF_AUTO_SET_VPP | CONF_AUTO_CHECK_VCC | |
| 239 | CONF_AUTO_SET_IO | CONF_ENABLE_IRQ; | ||
| 275 | if (ignore_cis_vcc) | 240 | if (ignore_cis_vcc) |
| 276 | link->config_flags &= ~CONF_AUTO_CHECK_VCC; | 241 | link->config_flags &= ~CONF_AUTO_CHECK_VCC; |
| 277 | ret = pcmcia_loop_config(link, spectrum_cs_config_check, NULL); | 242 | ret = pcmcia_loop_config(link, spectrum_cs_config_check, NULL); |
diff --git a/drivers/parport/parport_cs.c b/drivers/parport/parport_cs.c index 8c2a4733bc19..3730184a04a3 100644 --- a/drivers/parport/parport_cs.c +++ b/drivers/parport/parport_cs.c | |||
| @@ -100,9 +100,7 @@ static int parport_probe(struct pcmcia_device *link) | |||
| 100 | link->priv = info; | 100 | link->priv = info; |
| 101 | info->p_dev = link; | 101 | info->p_dev = link; |
| 102 | 102 | ||
| 103 | link->resource[0]->flags |= IO_DATA_PATH_WIDTH_8; | 103 | link->config_flags |= CONF_ENABLE_IRQ | CONF_AUTO_SET_IO; |
| 104 | link->resource[1]->flags |= IO_DATA_PATH_WIDTH_8; | ||
| 105 | link->config_flags |= CONF_ENABLE_IRQ; | ||
| 106 | 104 | ||
| 107 | return parport_config(link); | 105 | return parport_config(link); |
| 108 | } /* parport_attach */ | 106 | } /* parport_attach */ |
| @@ -133,27 +131,14 @@ static void parport_detach(struct pcmcia_device *link) | |||
| 133 | 131 | ||
| 134 | ======================================================================*/ | 132 | ======================================================================*/ |
| 135 | 133 | ||
| 136 | static int parport_config_check(struct pcmcia_device *p_dev, | 134 | static int parport_config_check(struct pcmcia_device *p_dev, void *priv_data) |
| 137 | cistpl_cftable_entry_t *cfg, | ||
| 138 | cistpl_cftable_entry_t *dflt, | ||
| 139 | void *priv_data) | ||
| 140 | { | 135 | { |
| 141 | if ((cfg->io.nwin > 0) || (dflt->io.nwin > 0)) { | 136 | p_dev->resource[0]->flags &= ~IO_DATA_PATH_WIDTH; |
| 142 | cistpl_io_t *io = (cfg->io.nwin) ? &cfg->io : &dflt->io; | 137 | p_dev->resource[0]->flags |= IO_DATA_PATH_WIDTH_8; |
| 143 | p_dev->io_lines = io->flags & CISTPL_IO_LINES_MASK; | 138 | p_dev->resource[1]->flags &= ~IO_DATA_PATH_WIDTH; |
| 144 | if (epp_mode) | 139 | p_dev->resource[1]->flags |= IO_DATA_PATH_WIDTH_8; |
| 145 | p_dev->config_index |= FORCE_EPP_MODE; | 140 | |
| 146 | p_dev->resource[0]->start = io->win[0].base; | 141 | return pcmcia_request_io(p_dev); |
| 147 | p_dev->resource[0]->end = io->win[0].len; | ||
| 148 | if (io->nwin == 2) { | ||
| 149 | p_dev->resource[1]->start = io->win[1].base; | ||
| 150 | p_dev->resource[1]->end = io->win[1].len; | ||
| 151 | } | ||
| 152 | if (pcmcia_request_io(p_dev) != 0) | ||
| 153 | return -ENODEV; | ||
| 154 | return 0; | ||
| 155 | } | ||
| 156 | return -ENODEV; | ||
| 157 | } | 142 | } |
| 158 | 143 | ||
| 159 | static int parport_config(struct pcmcia_device *link) | 144 | static int parport_config(struct pcmcia_device *link) |
| @@ -164,6 +149,9 @@ static int parport_config(struct pcmcia_device *link) | |||
| 164 | 149 | ||
| 165 | dev_dbg(&link->dev, "parport_config\n"); | 150 | dev_dbg(&link->dev, "parport_config\n"); |
| 166 | 151 | ||
| 152 | if (epp_mode) | ||
| 153 | link->config_index |= FORCE_EPP_MODE; | ||
| 154 | |||
| 167 | ret = pcmcia_loop_config(link, parport_config_check, NULL); | 155 | ret = pcmcia_loop_config(link, parport_config_check, NULL); |
| 168 | if (ret) | 156 | if (ret) |
| 169 | goto failed; | 157 | goto failed; |
diff --git a/drivers/pcmcia/pcmcia_cis.c b/drivers/pcmcia/pcmcia_cis.c index 160da0697335..e2c92415b892 100644 --- a/drivers/pcmcia/pcmcia_cis.c +++ b/drivers/pcmcia/pcmcia_cis.c | |||
| @@ -6,7 +6,7 @@ | |||
| 6 | * are Copyright (C) 1999 David A. Hinds. All Rights Reserved. | 6 | * are Copyright (C) 1999 David A. Hinds. All Rights Reserved. |
| 7 | * | 7 | * |
| 8 | * Copyright (C) 1999 David A. Hinds | 8 | * Copyright (C) 1999 David A. Hinds |
| 9 | * Copyright (C) 2004-2009 Dominik Brodowski | 9 | * Copyright (C) 2004-2010 Dominik Brodowski |
| 10 | * | 10 | * |
| 11 | * This program is free software; you can redistribute it and/or modify | 11 | * This program is free software; you can redistribute it and/or modify |
| 12 | * it under the terms of the GNU General Public License version 2 as | 12 | * it under the terms of the GNU General Public License version 2 as |
| @@ -125,13 +125,24 @@ next_entry: | |||
| 125 | return ret; | 125 | return ret; |
| 126 | } | 126 | } |
| 127 | 127 | ||
| 128 | |||
| 129 | /** | ||
| 130 | * pcmcia_io_cfg_data_width() - convert cfgtable to data path width parameter | ||
| 131 | */ | ||
| 132 | static int pcmcia_io_cfg_data_width(unsigned int flags) | ||
| 133 | { | ||
| 134 | if (!(flags & CISTPL_IO_8BIT)) | ||
| 135 | return IO_DATA_PATH_WIDTH_16; | ||
| 136 | if (!(flags & CISTPL_IO_16BIT)) | ||
| 137 | return IO_DATA_PATH_WIDTH_8; | ||
| 138 | return IO_DATA_PATH_WIDTH_AUTO; | ||
| 139 | } | ||
| 140 | |||
| 141 | |||
| 128 | struct pcmcia_cfg_mem { | 142 | struct pcmcia_cfg_mem { |
| 129 | struct pcmcia_device *p_dev; | 143 | struct pcmcia_device *p_dev; |
| 144 | int (*conf_check) (struct pcmcia_device *p_dev, void *priv_data); | ||
| 130 | void *priv_data; | 145 | void *priv_data; |
| 131 | int (*conf_check) (struct pcmcia_device *p_dev, | ||
| 132 | cistpl_cftable_entry_t *cfg, | ||
| 133 | cistpl_cftable_entry_t *dflt, | ||
| 134 | void *priv_data); | ||
| 135 | cisparse_t parse; | 146 | cisparse_t parse; |
| 136 | cistpl_cftable_entry_t dflt; | 147 | cistpl_cftable_entry_t dflt; |
| 137 | }; | 148 | }; |
| @@ -184,16 +195,63 @@ static int pcmcia_do_loop_config(tuple_t *tuple, cisparse_t *parse, void *priv) | |||
| 184 | if ((flags & CONF_AUTO_AUDIO) && (cfg->flags & CISTPL_CFTABLE_AUDIO)) | 195 | if ((flags & CONF_AUTO_AUDIO) && (cfg->flags & CISTPL_CFTABLE_AUDIO)) |
| 185 | p_dev->config_flags |= CONF_ENABLE_SPKR; | 196 | p_dev->config_flags |= CONF_ENABLE_SPKR; |
| 186 | 197 | ||
| 187 | return cfg_mem->conf_check(cfg_mem->p_dev, cfg, &cfg_mem->dflt, | 198 | |
| 188 | cfg_mem->priv_data); | 199 | /* IO window settings? */ |
| 200 | if (flags & CONF_AUTO_SET_IO) { | ||
| 201 | cistpl_io_t *io = (cfg->io.nwin) ? &cfg->io : &dflt->io; | ||
| 202 | int i = 0; | ||
| 203 | |||
| 204 | p_dev->resource[0]->start = p_dev->resource[0]->end = 0; | ||
| 205 | p_dev->resource[1]->start = p_dev->resource[1]->end = 0; | ||
| 206 | if (io->nwin == 0) | ||
| 207 | return -ENODEV; | ||
| 208 | |||
| 209 | p_dev->resource[0]->flags &= ~IO_DATA_PATH_WIDTH; | ||
| 210 | p_dev->resource[0]->flags |= | ||
| 211 | pcmcia_io_cfg_data_width(io->flags); | ||
| 212 | if (io->nwin > 1) { | ||
| 213 | /* For multifunction cards, by convention, we | ||
| 214 | * configure the network function with window 0, | ||
| 215 | * and serial with window 1 */ | ||
| 216 | i = (io->win[1].len > io->win[0].len); | ||
| 217 | p_dev->resource[1]->flags = p_dev->resource[0]->flags; | ||
| 218 | p_dev->resource[1]->start = io->win[1-i].base; | ||
| 219 | p_dev->resource[1]->end = io->win[1-i].len; | ||
| 220 | } | ||
| 221 | p_dev->resource[0]->start = io->win[i].base; | ||
| 222 | p_dev->resource[0]->end = io->win[i].len; | ||
| 223 | p_dev->io_lines = io->flags & CISTPL_IO_LINES_MASK; | ||
| 224 | } | ||
| 225 | |||
| 226 | /* MEM window settings? */ | ||
| 227 | if (flags & CONF_AUTO_SET_IOMEM) { | ||
| 228 | /* so far, we only set one memory window */ | ||
| 229 | cistpl_mem_t *mem = (cfg->mem.nwin) ? &cfg->mem : &dflt->mem; | ||
| 230 | |||
| 231 | p_dev->resource[2]->start = p_dev->resource[2]->end = 0; | ||
| 232 | if (mem->nwin == 0) | ||
| 233 | return -ENODEV; | ||
| 234 | |||
| 235 | p_dev->resource[2]->start = mem->win[0].host_addr; | ||
| 236 | p_dev->resource[2]->end = mem->win[0].len; | ||
| 237 | if (p_dev->resource[2]->end < 0x1000) | ||
| 238 | p_dev->resource[2]->end = 0x1000; | ||
| 239 | p_dev->card_addr = mem->win[0].card_addr; | ||
| 240 | } | ||
| 241 | |||
| 242 | dev_dbg(&p_dev->dev, | ||
| 243 | "checking configuration %x: %pr %pr %pr (%d lines)\n", | ||
| 244 | p_dev->config_index, p_dev->resource[0], p_dev->resource[1], | ||
| 245 | p_dev->resource[2], p_dev->io_lines); | ||
| 246 | |||
| 247 | return cfg_mem->conf_check(p_dev, cfg_mem->priv_data); | ||
| 189 | } | 248 | } |
| 190 | 249 | ||
| 191 | /** | 250 | /** |
| 192 | * pcmcia_loop_config() - loop over configuration options | 251 | * pcmcia_loop_config() - loop over configuration options |
| 193 | * @p_dev: the struct pcmcia_device which we need to loop for. | 252 | * @p_dev: the struct pcmcia_device which we need to loop for. |
| 194 | * @conf_check: function to call for each configuration option. | 253 | * @conf_check: function to call for each configuration option. |
| 195 | * It gets passed the struct pcmcia_device, the CIS data | 254 | * It gets passed the struct pcmcia_device and private data |
| 196 | * describing the configuration option, and private data | ||
| 197 | * being passed to pcmcia_loop_config() | 255 | * being passed to pcmcia_loop_config() |
| 198 | * @priv_data: private data to be passed to the conf_check function. | 256 | * @priv_data: private data to be passed to the conf_check function. |
| 199 | * | 257 | * |
| @@ -203,8 +261,6 @@ static int pcmcia_do_loop_config(tuple_t *tuple, cisparse_t *parse, void *priv) | |||
| 203 | */ | 261 | */ |
| 204 | int pcmcia_loop_config(struct pcmcia_device *p_dev, | 262 | int pcmcia_loop_config(struct pcmcia_device *p_dev, |
| 205 | int (*conf_check) (struct pcmcia_device *p_dev, | 263 | int (*conf_check) (struct pcmcia_device *p_dev, |
| 206 | cistpl_cftable_entry_t *cfg, | ||
| 207 | cistpl_cftable_entry_t *dflt, | ||
| 208 | void *priv_data), | 264 | void *priv_data), |
| 209 | void *priv_data) | 265 | void *priv_data) |
| 210 | { | 266 | { |
diff --git a/drivers/scsi/pcmcia/aha152x_stub.c b/drivers/scsi/pcmcia/aha152x_stub.c index 0b5fc2fa0589..bd9ce09b7ff8 100644 --- a/drivers/scsi/pcmcia/aha152x_stub.c +++ b/drivers/scsi/pcmcia/aha152x_stub.c | |||
| @@ -99,9 +99,7 @@ static int aha152x_probe(struct pcmcia_device *link) | |||
| 99 | info->p_dev = link; | 99 | info->p_dev = link; |
| 100 | link->priv = info; | 100 | link->priv = info; |
| 101 | 101 | ||
| 102 | link->resource[0]->end = 0x20; | 102 | link->config_flags |= CONF_ENABLE_IRQ | CONF_AUTO_SET_IO; |
| 103 | link->resource[0]->flags |= IO_DATA_PATH_WIDTH_AUTO; | ||
| 104 | link->config_flags |= CONF_ENABLE_IRQ; | ||
| 105 | link->config_regs = PRESENT_OPTION; | 103 | link->config_regs = PRESENT_OPTION; |
| 106 | 104 | ||
| 107 | return aha152x_config_cs(link); | 105 | return aha152x_config_cs(link); |
| @@ -121,24 +119,24 @@ static void aha152x_detach(struct pcmcia_device *link) | |||
| 121 | 119 | ||
| 122 | /*====================================================================*/ | 120 | /*====================================================================*/ |
| 123 | 121 | ||
| 124 | static int aha152x_config_check(struct pcmcia_device *p_dev, | 122 | static int aha152x_config_check(struct pcmcia_device *p_dev, void *priv_data) |
| 125 | cistpl_cftable_entry_t *cfg, | ||
| 126 | cistpl_cftable_entry_t *dflt, | ||
| 127 | void *priv_data) | ||
| 128 | { | 123 | { |
| 129 | p_dev->io_lines = 10; | 124 | p_dev->io_lines = 10; |
| 125 | |||
| 130 | /* For New Media T&J, look for a SCSI window */ | 126 | /* For New Media T&J, look for a SCSI window */ |
| 131 | if (cfg->io.win[0].len >= 0x20) | 127 | if ((p_dev->resource[0]->end < 0x20) && |
| 132 | p_dev->resource[0]->start = cfg->io.win[0].base; | 128 | (p_dev->resource[1]->end >= 0x20)) |
| 133 | else if ((cfg->io.nwin > 1) && | 129 | p_dev->resource[0]->start = p_dev->resource[1]->start; |
| 134 | (cfg->io.win[1].len >= 0x20)) | 130 | |
| 135 | p_dev->resource[0]->start = cfg->io.win[1].base; | 131 | if (p_dev->resource[0]->start >= 0xffff) |
| 136 | if ((cfg->io.nwin > 0) && | 132 | return -EINVAL; |
| 137 | (p_dev->resource[0]->start < 0xffff)) { | 133 | |
| 138 | if (!pcmcia_request_io(p_dev)) | 134 | p_dev->resource[1]->start = p_dev->resource[1]->end = 0; |
| 139 | return 0; | 135 | p_dev->resource[0]->end = 0x20; |
| 140 | } | 136 | p_dev->resource[0]->flags &= ~IO_DATA_PATH_WIDTH; |
| 141 | return -EINVAL; | 137 | p_dev->resource[0]->flags |= IO_DATA_PATH_WIDTH_AUTO; |
| 138 | |||
| 139 | return pcmcia_request_io(p_dev); | ||
| 142 | } | 140 | } |
| 143 | 141 | ||
| 144 | static int aha152x_config_cs(struct pcmcia_device *link) | 142 | static int aha152x_config_cs(struct pcmcia_device *link) |
diff --git a/drivers/scsi/pcmcia/fdomain_stub.c b/drivers/scsi/pcmcia/fdomain_stub.c index 3b9f311cb035..f2dc627e9da2 100644 --- a/drivers/scsi/pcmcia/fdomain_stub.c +++ b/drivers/scsi/pcmcia/fdomain_stub.c | |||
| @@ -82,9 +82,7 @@ static int fdomain_probe(struct pcmcia_device *link) | |||
| 82 | 82 | ||
| 83 | info->p_dev = link; | 83 | info->p_dev = link; |
| 84 | link->priv = info; | 84 | link->priv = info; |
| 85 | link->resource[0]->end = 0x10; | 85 | link->config_flags |= CONF_ENABLE_IRQ | CONF_AUTO_SET_IO; |
| 86 | link->resource[0]->flags |= IO_DATA_PATH_WIDTH_AUTO; | ||
| 87 | link->config_flags |= CONF_ENABLE_IRQ; | ||
| 88 | link->config_regs = PRESENT_OPTION; | 86 | link->config_regs = PRESENT_OPTION; |
| 89 | 87 | ||
| 90 | return fdomain_config(link); | 88 | return fdomain_config(link); |
| @@ -103,13 +101,12 @@ static void fdomain_detach(struct pcmcia_device *link) | |||
| 103 | 101 | ||
| 104 | /*====================================================================*/ | 102 | /*====================================================================*/ |
| 105 | 103 | ||
| 106 | static int fdomain_config_check(struct pcmcia_device *p_dev, | 104 | static int fdomain_config_check(struct pcmcia_device *p_dev, void *priv_data) |
| 107 | cistpl_cftable_entry_t *cfg, | ||
| 108 | cistpl_cftable_entry_t *dflt, | ||
| 109 | void *priv_data) | ||
| 110 | { | 105 | { |
| 111 | p_dev->io_lines = 10; | 106 | p_dev->io_lines = 10; |
| 112 | p_dev->resource[0]->start = cfg->io.win[0].base; | 107 | p_dev->resource[0]->end = 0x10; |
| 108 | p_dev->resource[0]->flags &= ~IO_DATA_PATH_WIDTH; | ||
| 109 | p_dev->resource[0]->flags |= IO_DATA_PATH_WIDTH_AUTO; | ||
| 113 | return pcmcia_request_io(p_dev); | 110 | return pcmcia_request_io(p_dev); |
| 114 | } | 111 | } |
| 115 | 112 | ||
diff --git a/drivers/scsi/pcmcia/nsp_cs.c b/drivers/scsi/pcmcia/nsp_cs.c index 344d49900b4c..3b90ad9d1956 100644 --- a/drivers/scsi/pcmcia/nsp_cs.c +++ b/drivers/scsi/pcmcia/nsp_cs.c | |||
| @@ -1556,13 +1556,6 @@ static int nsp_cs_probe(struct pcmcia_device *link) | |||
| 1556 | 1556 | ||
| 1557 | nsp_dbg(NSP_DEBUG_INIT, "info=0x%p", info); | 1557 | nsp_dbg(NSP_DEBUG_INIT, "info=0x%p", info); |
| 1558 | 1558 | ||
| 1559 | /* The io structure describes IO port mapping */ | ||
| 1560 | link->resource[0]->end = 0x10; | ||
| 1561 | link->resource[0]->flags = IO_DATA_PATH_WIDTH_AUTO; | ||
| 1562 | |||
| 1563 | /* General socket configuration */ | ||
| 1564 | link->config_flags |= CONF_ENABLE_IRQ; | ||
| 1565 | |||
| 1566 | ret = nsp_cs_config(link); | 1559 | ret = nsp_cs_config(link); |
| 1567 | 1560 | ||
| 1568 | nsp_dbg(NSP_DEBUG_INIT, "link=0x%p", link); | 1561 | nsp_dbg(NSP_DEBUG_INIT, "link=0x%p", link); |
| @@ -1594,50 +1587,27 @@ static void nsp_cs_detach(struct pcmcia_device *link) | |||
| 1594 | ethernet device available to the system. | 1587 | ethernet device available to the system. |
| 1595 | ======================================================================*/ | 1588 | ======================================================================*/ |
| 1596 | 1589 | ||
| 1597 | static int nsp_cs_config_check(struct pcmcia_device *p_dev, | 1590 | static int nsp_cs_config_check(struct pcmcia_device *p_dev, void *priv_data) |
| 1598 | cistpl_cftable_entry_t *cfg, | ||
| 1599 | cistpl_cftable_entry_t *dflt, | ||
| 1600 | void *priv_data) | ||
| 1601 | { | 1591 | { |
| 1602 | nsp_hw_data *data = priv_data; | 1592 | nsp_hw_data *data = priv_data; |
| 1603 | 1593 | ||
| 1604 | if (cfg->index == 0) | 1594 | if (p_dev->config_index == 0) |
| 1605 | return -ENODEV; | 1595 | return -ENODEV; |
| 1606 | 1596 | ||
| 1607 | /* IO window settings */ | 1597 | /* This reserves IO space but doesn't actually enable it */ |
| 1608 | p_dev->resource[0]->end = p_dev->resource[1]->end = 0; | 1598 | if (pcmcia_request_io(p_dev) != 0) |
| 1609 | if ((cfg->io.nwin > 0) || (dflt->io.nwin > 0)) { | 1599 | goto next_entry; |
| 1610 | cistpl_io_t *io = (cfg->io.nwin) ? &cfg->io : &dflt->io; | ||
| 1611 | p_dev->io_lines = io->flags & CISTPL_IO_LINES_MASK; | ||
| 1612 | p_dev->resource[0]->flags &= ~IO_DATA_PATH_WIDTH; | ||
| 1613 | p_dev->resource[0]->flags |= | ||
| 1614 | pcmcia_io_cfg_data_width(io->flags); | ||
| 1615 | p_dev->resource[0]->start = io->win[0].base; | ||
| 1616 | p_dev->resource[0]->end = io->win[0].len; | ||
| 1617 | if (io->nwin > 1) { | ||
| 1618 | p_dev->resource[1]->flags = p_dev->resource[0]->flags; | ||
| 1619 | p_dev->resource[1]->start = io->win[1].base; | ||
| 1620 | p_dev->resource[1]->end = io->win[1].len; | ||
| 1621 | } | ||
| 1622 | /* This reserves IO space but doesn't actually enable it */ | ||
| 1623 | if (pcmcia_request_io(p_dev) != 0) | ||
| 1624 | goto next_entry; | ||
| 1625 | } | ||
| 1626 | 1600 | ||
| 1627 | if ((cfg->mem.nwin > 0) || (dflt->mem.nwin > 0)) { | 1601 | if (resource_size(p_dev->resource[2])) { |
| 1628 | cistpl_mem_t *mem = | ||
| 1629 | (cfg->mem.nwin) ? &cfg->mem : &dflt->mem; | ||
| 1630 | p_dev->resource[2]->flags |= (WIN_DATA_WIDTH_16 | | 1602 | p_dev->resource[2]->flags |= (WIN_DATA_WIDTH_16 | |
| 1631 | WIN_MEMORY_TYPE_CM | | 1603 | WIN_MEMORY_TYPE_CM | |
| 1632 | WIN_ENABLE); | 1604 | WIN_ENABLE); |
| 1633 | p_dev->resource[2]->start = mem->win[0].host_addr; | ||
| 1634 | p_dev->resource[2]->end = mem->win[0].len; | ||
| 1635 | if (p_dev->resource[2]->end < 0x1000) | 1605 | if (p_dev->resource[2]->end < 0x1000) |
| 1636 | p_dev->resource[2]->end = 0x1000; | 1606 | p_dev->resource[2]->end = 0x1000; |
| 1637 | if (pcmcia_request_window(p_dev, p_dev->resource[2], 0) != 0) | 1607 | if (pcmcia_request_window(p_dev, p_dev->resource[2], 0) != 0) |
| 1638 | goto next_entry; | 1608 | goto next_entry; |
| 1639 | if (pcmcia_map_mem_page(p_dev, p_dev->resource[2], | 1609 | if (pcmcia_map_mem_page(p_dev, p_dev->resource[2], |
| 1640 | mem->win[0].card_addr) != 0) | 1610 | p_dev->card_addr) != 0) |
| 1641 | goto next_entry; | 1611 | goto next_entry; |
| 1642 | 1612 | ||
| 1643 | data->MmioAddress = (unsigned long) | 1613 | data->MmioAddress = (unsigned long) |
| @@ -1664,7 +1634,8 @@ static int nsp_cs_config(struct pcmcia_device *link) | |||
| 1664 | nsp_dbg(NSP_DEBUG_INIT, "in"); | 1634 | nsp_dbg(NSP_DEBUG_INIT, "in"); |
| 1665 | 1635 | ||
| 1666 | link->config_flags |= CONF_ENABLE_IRQ | CONF_AUTO_CHECK_VCC | | 1636 | link->config_flags |= CONF_ENABLE_IRQ | CONF_AUTO_CHECK_VCC | |
| 1667 | CONF_AUTO_SET_VPP | CONF_AUTO_AUDIO; | 1637 | CONF_AUTO_SET_VPP | CONF_AUTO_AUDIO | CONF_AUTO_SET_IOMEM | |
| 1638 | CONF_AUTO_SET_IO; | ||
| 1668 | 1639 | ||
| 1669 | ret = pcmcia_loop_config(link, nsp_cs_config_check, data); | 1640 | ret = pcmcia_loop_config(link, nsp_cs_config_check, data); |
| 1670 | if (ret) | 1641 | if (ret) |
diff --git a/drivers/scsi/pcmcia/qlogic_stub.c b/drivers/scsi/pcmcia/qlogic_stub.c index 468fd12fe98d..e8a06e3a384c 100644 --- a/drivers/scsi/pcmcia/qlogic_stub.c +++ b/drivers/scsi/pcmcia/qlogic_stub.c | |||
| @@ -155,9 +155,7 @@ static int qlogic_probe(struct pcmcia_device *link) | |||
| 155 | return -ENOMEM; | 155 | return -ENOMEM; |
| 156 | info->p_dev = link; | 156 | info->p_dev = link; |
| 157 | link->priv = info; | 157 | link->priv = info; |
| 158 | link->resource[0]->end = 16; | 158 | link->config_flags |= CONF_ENABLE_IRQ | CONF_AUTO_SET_IO; |
| 159 | link->resource[0]->flags |= IO_DATA_PATH_WIDTH_AUTO; | ||
| 160 | link->config_flags |= CONF_ENABLE_IRQ; | ||
| 161 | link->config_regs = PRESENT_OPTION; | 159 | link->config_regs = PRESENT_OPTION; |
| 162 | 160 | ||
| 163 | return qlogic_config(link); | 161 | return qlogic_config(link); |
| @@ -176,14 +174,11 @@ static void qlogic_detach(struct pcmcia_device *link) | |||
| 176 | 174 | ||
| 177 | /*====================================================================*/ | 175 | /*====================================================================*/ |
| 178 | 176 | ||
| 179 | static int qlogic_config_check(struct pcmcia_device *p_dev, | 177 | static int qlogic_config_check(struct pcmcia_device *p_dev, void *priv_data) |
| 180 | cistpl_cftable_entry_t *cfg, | ||
| 181 | cistpl_cftable_entry_t *dflt, | ||
| 182 | void *priv_data) | ||
| 183 | { | 178 | { |
| 184 | p_dev->io_lines = 10; | 179 | p_dev->io_lines = 10; |
| 185 | p_dev->resource[0]->start = cfg->io.win[0].base; | 180 | p_dev->resource[0]->flags &= ~IO_DATA_PATH_WIDTH; |
| 186 | p_dev->resource[0]->end = cfg->io.win[0].len; | 181 | p_dev->resource[0]->flags |= IO_DATA_PATH_WIDTH_AUTO; |
| 187 | 182 | ||
| 188 | if (p_dev->resource[0]->start == 0) | 183 | if (p_dev->resource[0]->start == 0) |
| 189 | return -ENODEV; | 184 | return -ENODEV; |
diff --git a/drivers/scsi/pcmcia/sym53c500_cs.c b/drivers/scsi/pcmcia/sym53c500_cs.c index 7a0bb9aea042..6ceb57c355fa 100644 --- a/drivers/scsi/pcmcia/sym53c500_cs.c +++ b/drivers/scsi/pcmcia/sym53c500_cs.c | |||
| @@ -683,14 +683,11 @@ static struct scsi_host_template sym53c500_driver_template = { | |||
| 683 | .shost_attrs = SYM53C500_shost_attrs | 683 | .shost_attrs = SYM53C500_shost_attrs |
| 684 | }; | 684 | }; |
| 685 | 685 | ||
| 686 | static int SYM53C500_config_check(struct pcmcia_device *p_dev, | 686 | static int SYM53C500_config_check(struct pcmcia_device *p_dev, void *priv_data) |
| 687 | cistpl_cftable_entry_t *cfg, | ||
| 688 | cistpl_cftable_entry_t *dflt, | ||
| 689 | void *priv_data) | ||
| 690 | { | 687 | { |
| 691 | p_dev->io_lines = 10; | 688 | p_dev->io_lines = 10; |
| 692 | p_dev->resource[0]->start = cfg->io.win[0].base; | 689 | p_dev->resource[0]->flags &= ~IO_DATA_PATH_WIDTH; |
| 693 | p_dev->resource[0]->end = cfg->io.win[0].len; | 690 | p_dev->resource[0]->flags |= IO_DATA_PATH_WIDTH_AUTO; |
| 694 | 691 | ||
| 695 | if (p_dev->resource[0]->start == 0) | 692 | if (p_dev->resource[0]->start == 0) |
| 696 | return -ENODEV; | 693 | return -ENODEV; |
| @@ -857,9 +854,7 @@ SYM53C500_probe(struct pcmcia_device *link) | |||
| 857 | return -ENOMEM; | 854 | return -ENOMEM; |
| 858 | info->p_dev = link; | 855 | info->p_dev = link; |
| 859 | link->priv = info; | 856 | link->priv = info; |
| 860 | link->resource[0]->end = 16; | 857 | link->config_flags |= CONF_ENABLE_IRQ | CONF_AUTO_SET_IO; |
| 861 | link->resource[0]->flags |= IO_DATA_PATH_WIDTH_AUTO; | ||
| 862 | link->config_flags |= CONF_ENABLE_IRQ; | ||
| 863 | 858 | ||
| 864 | return SYM53C500_config(link); | 859 | return SYM53C500_config(link); |
| 865 | } /* SYM53C500_attach */ | 860 | } /* SYM53C500_attach */ |
diff --git a/drivers/serial/serial_cs.c b/drivers/serial/serial_cs.c index a796a93fe39c..422520342936 100644 --- a/drivers/serial/serial_cs.c +++ b/drivers/serial/serial_cs.c | |||
| @@ -424,41 +424,45 @@ static int pfc_config(struct pcmcia_device *p_dev) | |||
| 424 | return -ENODEV; | 424 | return -ENODEV; |
| 425 | } | 425 | } |
| 426 | 426 | ||
| 427 | static int simple_config_check(struct pcmcia_device *p_dev, | 427 | static int simple_config_check(struct pcmcia_device *p_dev, void *priv_data) |
| 428 | cistpl_cftable_entry_t *cf, | ||
| 429 | cistpl_cftable_entry_t *dflt, | ||
| 430 | void *priv_data) | ||
| 431 | { | 428 | { |
| 432 | static const int size_table[2] = { 8, 16 }; | 429 | static const int size_table[2] = { 8, 16 }; |
| 433 | int *try = priv_data; | 430 | int *try = priv_data; |
| 434 | 431 | ||
| 435 | p_dev->io_lines = ((*try & 0x1) == 0) ? | 432 | if (p_dev->resource[0]->start == 0) |
| 436 | 16 : cf->io.flags & CISTPL_IO_LINES_MASK; | 433 | return -ENODEV; |
| 437 | 434 | ||
| 438 | if ((cf->io.nwin > 0) && (cf->io.win[0].len == size_table[(*try >> 1)]) | 435 | if ((*try & 0x1) == 0) |
| 439 | && (cf->io.win[0].base != 0)) { | 436 | p_dev->io_lines = 16; |
| 440 | p_dev->resource[0]->start = cf->io.win[0].base; | 437 | |
| 441 | if (!pcmcia_request_io(p_dev)) | 438 | if (p_dev->resource[0]->end != size_table[(*try >> 1)]) |
| 442 | return 0; | 439 | return -ENODEV; |
| 443 | } | 440 | |
| 444 | return -EINVAL; | 441 | p_dev->resource[0]->end = 8; |
| 442 | p_dev->resource[0]->flags &= ~IO_DATA_PATH_WIDTH; | ||
| 443 | p_dev->resource[0]->flags |= IO_DATA_PATH_WIDTH_8; | ||
| 444 | |||
| 445 | return pcmcia_request_io(p_dev); | ||
| 445 | } | 446 | } |
| 446 | 447 | ||
| 447 | static int simple_config_check_notpicky(struct pcmcia_device *p_dev, | 448 | static int simple_config_check_notpicky(struct pcmcia_device *p_dev, |
| 448 | cistpl_cftable_entry_t *cf, | ||
| 449 | cistpl_cftable_entry_t *dflt, | ||
| 450 | void *priv_data) | 449 | void *priv_data) |
| 451 | { | 450 | { |
| 452 | static const unsigned int base[5] = { 0x3f8, 0x2f8, 0x3e8, 0x2e8, 0x0 }; | 451 | static const unsigned int base[5] = { 0x3f8, 0x2f8, 0x3e8, 0x2e8, 0x0 }; |
| 453 | int j; | 452 | int j; |
| 454 | 453 | ||
| 455 | if ((cf->io.nwin > 0) && ((cf->io.flags & CISTPL_IO_LINES_MASK) <= 3)) { | 454 | if (p_dev->io_lines > 3) |
| 456 | for (j = 0; j < 5; j++) { | 455 | return -ENODEV; |
| 457 | p_dev->resource[0]->start = base[j]; | 456 | |
| 458 | p_dev->io_lines = base[j] ? 16 : 3; | 457 | p_dev->resource[0]->flags &= ~IO_DATA_PATH_WIDTH; |
| 459 | if (!pcmcia_request_io(p_dev)) | 458 | p_dev->resource[0]->flags |= IO_DATA_PATH_WIDTH_8; |
| 460 | return 0; | 459 | p_dev->resource[0]->end = 8; |
| 461 | } | 460 | |
| 461 | for (j = 0; j < 5; j++) { | ||
| 462 | p_dev->resource[0]->start = base[j]; | ||
| 463 | p_dev->io_lines = base[j] ? 16 : 3; | ||
| 464 | if (!pcmcia_request_io(p_dev)) | ||
| 465 | return 0; | ||
| 462 | } | 466 | } |
| 463 | return -ENODEV; | 467 | return -ENODEV; |
| 464 | } | 468 | } |
| @@ -468,12 +472,9 @@ static int simple_config(struct pcmcia_device *link) | |||
| 468 | struct serial_info *info = link->priv; | 472 | struct serial_info *info = link->priv; |
| 469 | int i = -ENODEV, try; | 473 | int i = -ENODEV, try; |
| 470 | 474 | ||
| 471 | link->resource[0]->flags |= IO_DATA_PATH_WIDTH_8; | ||
| 472 | link->resource[0]->end = 8; | ||
| 473 | |||
| 474 | /* First pass: look for a config entry that looks normal. | 475 | /* First pass: look for a config entry that looks normal. |
| 475 | * Two tries: without IO aliases, then with aliases */ | 476 | * Two tries: without IO aliases, then with aliases */ |
| 476 | link->config_flags |= CONF_AUTO_SET_VPP; | 477 | link->config_flags |= CONF_AUTO_SET_VPP | CONF_AUTO_SET_IO; |
| 477 | for (try = 0; try < 4; try++) | 478 | for (try = 0; try < 4; try++) |
| 478 | if (!pcmcia_loop_config(link, simple_config_check, &try)) | 479 | if (!pcmcia_loop_config(link, simple_config_check, &try)) |
| 479 | goto found_port; | 480 | goto found_port; |
| @@ -503,43 +504,44 @@ found_port: | |||
| 503 | return setup_serial(link, info, link->resource[0]->start, link->irq); | 504 | return setup_serial(link, info, link->resource[0]->start, link->irq); |
| 504 | } | 505 | } |
| 505 | 506 | ||
| 506 | static int multi_config_check(struct pcmcia_device *p_dev, | 507 | static int multi_config_check(struct pcmcia_device *p_dev, void *priv_data) |
| 507 | cistpl_cftable_entry_t *cf, | ||
| 508 | cistpl_cftable_entry_t *dflt, | ||
| 509 | void *priv_data) | ||
| 510 | { | 508 | { |
| 511 | int *base2 = priv_data; | 509 | int *multi = priv_data; |
| 510 | |||
| 511 | if (p_dev->resource[1]->end) | ||
| 512 | return -EINVAL; | ||
| 512 | 513 | ||
| 513 | /* The quad port cards have bad CIS's, so just look for a | 514 | /* The quad port cards have bad CIS's, so just look for a |
| 514 | window larger than 8 ports and assume it will be right */ | 515 | window larger than 8 ports and assume it will be right */ |
| 515 | if ((cf->io.nwin == 1) && (cf->io.win[0].len > 8)) { | 516 | if (p_dev->resource[0]->end <= 8) |
| 516 | p_dev->resource[0]->start = cf->io.win[0].base; | 517 | return -EINVAL; |
| 517 | p_dev->io_lines = cf->io.flags & CISTPL_IO_LINES_MASK; | 518 | |
| 518 | if (!pcmcia_request_io(p_dev)) { | 519 | p_dev->resource[0]->flags &= ~IO_DATA_PATH_WIDTH; |
| 519 | *base2 = p_dev->resource[0]->start + 8; | 520 | p_dev->resource[0]->flags |= IO_DATA_PATH_WIDTH_8; |
| 520 | return 0; | 521 | p_dev->resource[0]->end = *multi * 8; |
| 521 | } | 522 | |
| 522 | } | 523 | if (pcmcia_request_io(p_dev)) |
| 523 | return -ENODEV; | 524 | return -ENODEV; |
| 525 | return 0; | ||
| 524 | } | 526 | } |
| 525 | 527 | ||
| 526 | static int multi_config_check_notpicky(struct pcmcia_device *p_dev, | 528 | static int multi_config_check_notpicky(struct pcmcia_device *p_dev, |
| 527 | cistpl_cftable_entry_t *cf, | ||
| 528 | cistpl_cftable_entry_t *dflt, | ||
| 529 | void *priv_data) | 529 | void *priv_data) |
| 530 | { | 530 | { |
| 531 | int *base2 = priv_data; | 531 | int *base2 = priv_data; |
| 532 | 532 | ||
| 533 | if (cf->io.nwin == 2) { | 533 | if (!p_dev->resource[0]->end || !p_dev->resource[1]->end) |
| 534 | p_dev->resource[0]->start = cf->io.win[0].base; | 534 | return -ENODEV; |
| 535 | p_dev->resource[1]->start = cf->io.win[1].base; | 535 | |
| 536 | p_dev->io_lines = cf->io.flags & CISTPL_IO_LINES_MASK; | 536 | p_dev->resource[0]->end = p_dev->resource[1]->end = 8; |
| 537 | if (!pcmcia_request_io(p_dev)) { | 537 | p_dev->resource[0]->flags &= ~IO_DATA_PATH_WIDTH; |
| 538 | *base2 = p_dev->resource[1]->start; | 538 | p_dev->resource[0]->flags |= IO_DATA_PATH_WIDTH_8; |
| 539 | return 0; | 539 | |
| 540 | } | 540 | if (pcmcia_request_io(p_dev)) |
| 541 | } | 541 | return -ENODEV; |
| 542 | return -ENODEV; | 542 | |
| 543 | *base2 = p_dev->resource[0]->start + 8; | ||
| 544 | return 0; | ||
| 543 | } | 545 | } |
| 544 | 546 | ||
| 545 | static int multi_config(struct pcmcia_device *link) | 547 | static int multi_config(struct pcmcia_device *link) |
| @@ -547,12 +549,12 @@ static int multi_config(struct pcmcia_device *link) | |||
| 547 | struct serial_info *info = link->priv; | 549 | struct serial_info *info = link->priv; |
| 548 | int i, base2 = 0; | 550 | int i, base2 = 0; |
| 549 | 551 | ||
| 552 | link->config_flags |= CONF_AUTO_SET_IO; | ||
| 550 | /* First, look for a generic full-sized window */ | 553 | /* First, look for a generic full-sized window */ |
| 551 | link->resource[0]->flags |= IO_DATA_PATH_WIDTH_8; | 554 | if (!pcmcia_loop_config(link, multi_config_check, &info->multi)) |
| 552 | link->resource[0]->end = info->multi * 8; | 555 | base2 = link->resource[0]->start + 8; |
| 553 | if (pcmcia_loop_config(link, multi_config_check, &base2)) { | 556 | else { |
| 554 | /* If that didn't work, look for two windows */ | 557 | /* If that didn't work, look for two windows */ |
| 555 | link->resource[0]->end = link->resource[1]->end = 8; | ||
| 556 | info->multi = 2; | 558 | info->multi = 2; |
| 557 | if (pcmcia_loop_config(link, multi_config_check_notpicky, | 559 | if (pcmcia_loop_config(link, multi_config_check_notpicky, |
| 558 | &base2)) { | 560 | &base2)) { |
| @@ -587,7 +589,7 @@ static int multi_config(struct pcmcia_device *link) | |||
| 587 | link->config_index == 3) { | 589 | link->config_index == 3) { |
| 588 | err = setup_serial(link, info, base2, | 590 | err = setup_serial(link, info, base2, |
| 589 | link->irq); | 591 | link->irq); |
| 590 | base2 = link->resource[0]->start;; | 592 | base2 = link->resource[0]->start; |
| 591 | } else { | 593 | } else { |
| 592 | err = setup_serial(link, info, link->resource[0]->start, | 594 | err = setup_serial(link, info, link->resource[0]->start, |
| 593 | link->irq); | 595 | link->irq); |
| @@ -611,18 +613,18 @@ static int multi_config(struct pcmcia_device *link) | |||
| 611 | return 0; | 613 | return 0; |
| 612 | } | 614 | } |
| 613 | 615 | ||
| 614 | static int serial_check_for_multi(struct pcmcia_device *p_dev, | 616 | static int serial_check_for_multi(struct pcmcia_device *p_dev, void *priv_data) |
| 615 | cistpl_cftable_entry_t *cf, | ||
| 616 | cistpl_cftable_entry_t *dflt, | ||
| 617 | void *priv_data) | ||
| 618 | { | 617 | { |
| 619 | struct serial_info *info = p_dev->priv; | 618 | struct serial_info *info = p_dev->priv; |
| 620 | 619 | ||
| 621 | if ((cf->io.nwin == 1) && (cf->io.win[0].len % 8 == 0)) | 620 | if (!p_dev->resource[0]->end) |
| 622 | info->multi = cf->io.win[0].len >> 3; | 621 | return -EINVAL; |
| 622 | |||
| 623 | if ((!p_dev->resource[1]->end) && (p_dev->resource[0]->end % 8 == 0)) | ||
| 624 | info->multi = p_dev->resource[0]->end >> 3; | ||
| 623 | 625 | ||
| 624 | if ((cf->io.nwin == 2) && (cf->io.win[0].len == 8) && | 626 | if ((p_dev->resource[1]->end) && (p_dev->resource[0]->end == 8) |
| 625 | (cf->io.win[1].len == 8)) | 627 | && (p_dev->resource[1]->end == 8)) |
| 626 | info->multi = 2; | 628 | info->multi = 2; |
| 627 | 629 | ||
| 628 | return 0; /* break */ | 630 | return 0; /* break */ |
diff --git a/drivers/staging/comedi/drivers/cb_das16_cs.c b/drivers/staging/comedi/drivers/cb_das16_cs.c index 678fbf67d7a8..c43c68922c74 100644 --- a/drivers/staging/comedi/drivers/cb_das16_cs.c +++ b/drivers/staging/comedi/drivers/cb_das16_cs.c | |||
| @@ -710,36 +710,12 @@ static void das16cs_pcmcia_detach(struct pcmcia_device *link) | |||
| 710 | 710 | ||
| 711 | 711 | ||
| 712 | static int das16cs_pcmcia_config_loop(struct pcmcia_device *p_dev, | 712 | static int das16cs_pcmcia_config_loop(struct pcmcia_device *p_dev, |
| 713 | cistpl_cftable_entry_t *cfg, | ||
| 714 | cistpl_cftable_entry_t *dflt, | ||
| 715 | void *priv_data) | 713 | void *priv_data) |
| 716 | { | 714 | { |
| 717 | if (cfg->index == 0) | 715 | if (p_dev->config_index == 0) |
| 718 | return -EINVAL; | 716 | return -EINVAL; |
| 719 | 717 | ||
| 720 | /* Do we need to allocate an interrupt? */ | 718 | return pcmcia_request_io(p_dev); |
| 721 | p_dev->config_flags |= CONF_ENABLE_IRQ; | ||
| 722 | |||
| 723 | /* IO window settings */ | ||
| 724 | p_dev->resource[0]->end = p_dev->resource[1]->end = 0; | ||
| 725 | if ((cfg->io.nwin > 0) || (dflt->io.nwin > 0)) { | ||
| 726 | cistpl_io_t *io = (cfg->io.nwin) ? &cfg->io : &dflt->io; | ||
| 727 | p_dev->io_lines = io->flags & CISTPL_IO_LINES_MASK; | ||
| 728 | p_dev->resource[0]->flags &= ~IO_DATA_PATH_WIDTH; | ||
| 729 | p_dev->resource[0]->flags |= | ||
| 730 | pcmcia_io_cfg_data_width(io->flags); | ||
| 731 | p_dev->resource[0]->start = io->win[0].base; | ||
| 732 | p_dev->resource[0]->end = io->win[0].len; | ||
| 733 | if (io->nwin > 1) { | ||
| 734 | p_dev->resource[1]->flags = p_dev->resource[0]->flags; | ||
| 735 | p_dev->resource[1]->start = io->win[1].base; | ||
| 736 | p_dev->resource[1]->end = io->win[1].len; | ||
| 737 | } | ||
| 738 | /* This reserves IO space but doesn't actually enable it */ | ||
| 739 | return pcmcia_request_io(p_dev); | ||
| 740 | } | ||
| 741 | |||
| 742 | return 0; | ||
| 743 | } | 719 | } |
| 744 | 720 | ||
| 745 | static void das16cs_pcmcia_config(struct pcmcia_device *link) | 721 | static void das16cs_pcmcia_config(struct pcmcia_device *link) |
| @@ -748,6 +724,9 @@ static void das16cs_pcmcia_config(struct pcmcia_device *link) | |||
| 748 | 724 | ||
| 749 | dev_dbg(&link->dev, "das16cs_pcmcia_config\n"); | 725 | dev_dbg(&link->dev, "das16cs_pcmcia_config\n"); |
| 750 | 726 | ||
| 727 | /* Do we need to allocate an interrupt? */ | ||
| 728 | link->config_flags |= CONF_ENABLE_IRQ | CONF_AUTO_SET_IO; | ||
| 729 | |||
| 751 | ret = pcmcia_loop_config(link, das16cs_pcmcia_config_loop, NULL); | 730 | ret = pcmcia_loop_config(link, das16cs_pcmcia_config_loop, NULL); |
| 752 | if (ret) { | 731 | if (ret) { |
| 753 | dev_warn(&link->dev, "no configuration found\n"); | 732 | dev_warn(&link->dev, "no configuration found\n"); |
diff --git a/drivers/staging/comedi/drivers/das08_cs.c b/drivers/staging/comedi/drivers/das08_cs.c index 12a96b7a43ad..d3959093381b 100644 --- a/drivers/staging/comedi/drivers/das08_cs.c +++ b/drivers/staging/comedi/drivers/das08_cs.c | |||
| @@ -192,35 +192,12 @@ static void das08_pcmcia_detach(struct pcmcia_device *link) | |||
| 192 | 192 | ||
| 193 | 193 | ||
| 194 | static int das08_pcmcia_config_loop(struct pcmcia_device *p_dev, | 194 | static int das08_pcmcia_config_loop(struct pcmcia_device *p_dev, |
| 195 | cistpl_cftable_entry_t *cfg, | ||
| 196 | cistpl_cftable_entry_t *dflt, | ||
| 197 | void *priv_data) | 195 | void *priv_data) |
| 198 | { | 196 | { |
| 199 | if (cfg->index == 0) | 197 | if (p_dev->config_index == 0) |
| 200 | return -ENODEV; | 198 | return -EINVAL; |
| 201 | 199 | ||
| 202 | /* Do we need to allocate an interrupt? */ | 200 | return pcmcia_request_io(p_dev); |
| 203 | p_dev->config_flags |= CONF_ENABLE_IRQ; | ||
| 204 | |||
| 205 | /* IO window settings */ | ||
| 206 | p_dev->resource[0]->end = p_dev->resource[1]->end = 0; | ||
| 207 | if ((cfg->io.nwin > 0) || (dflt->io.nwin > 0)) { | ||
| 208 | cistpl_io_t *io = (cfg->io.nwin) ? &cfg->io : &dflt->io; | ||
| 209 | p_dev->io_lines = io->flags & CISTPL_IO_LINES_MASK; | ||
| 210 | p_dev->resource[0]->flags &= ~IO_DATA_PATH_WIDTH; | ||
| 211 | p_dev->resource[0]->flags |= | ||
| 212 | pcmcia_io_cfg_data_width(io->flags); | ||
| 213 | p_dev->resource[0]->start = io->win[0].base; | ||
| 214 | p_dev->resource[0]->end = io->win[0].len; | ||
| 215 | if (io->nwin > 1) { | ||
| 216 | p_dev->resource[1]->flags = p_dev->resource[0]->flags; | ||
| 217 | p_dev->resource[1]->start = io->win[1].base; | ||
| 218 | p_dev->resource[1]->end = io->win[1].len; | ||
| 219 | } | ||
| 220 | /* This reserves IO space but doesn't actually enable it */ | ||
| 221 | return pcmcia_request_io(p_dev); | ||
| 222 | } | ||
| 223 | return 0; | ||
| 224 | } | 201 | } |
| 225 | 202 | ||
| 226 | 203 | ||
| @@ -238,6 +215,8 @@ static void das08_pcmcia_config(struct pcmcia_device *link) | |||
| 238 | 215 | ||
| 239 | dev_dbg(&link->dev, "das08_pcmcia_config\n"); | 216 | dev_dbg(&link->dev, "das08_pcmcia_config\n"); |
| 240 | 217 | ||
| 218 | link->config_flags |= CONF_ENABLE_IRQ | CONF_AUTO_SET_IO; | ||
| 219 | |||
| 241 | ret = pcmcia_loop_config(link, das08_pcmcia_config_loop, NULL); | 220 | ret = pcmcia_loop_config(link, das08_pcmcia_config_loop, NULL); |
| 242 | if (ret) { | 221 | if (ret) { |
| 243 | dev_warn(&link->dev, "no configuration found\n"); | 222 | dev_warn(&link->dev, "no configuration found\n"); |
diff --git a/drivers/staging/comedi/drivers/ni_daq_700.c b/drivers/staging/comedi/drivers/ni_daq_700.c index f22dc0f2a8d6..7129b0ca4c8b 100644 --- a/drivers/staging/comedi/drivers/ni_daq_700.c +++ b/drivers/staging/comedi/drivers/ni_daq_700.c | |||
| @@ -530,35 +530,12 @@ static void dio700_cs_detach(struct pcmcia_device *link) | |||
| 530 | ======================================================================*/ | 530 | ======================================================================*/ |
| 531 | 531 | ||
| 532 | static int dio700_pcmcia_config_loop(struct pcmcia_device *p_dev, | 532 | static int dio700_pcmcia_config_loop(struct pcmcia_device *p_dev, |
| 533 | cistpl_cftable_entry_t *cfg, | ||
| 534 | cistpl_cftable_entry_t *dflt, | ||
| 535 | void *priv_data) | 533 | void *priv_data) |
| 536 | { | 534 | { |
| 537 | if (cfg->index == 0) | 535 | if (p_dev->config_index == 0) |
| 538 | return -ENODEV; | 536 | return -EINVAL; |
| 539 | |||
| 540 | /* IO window settings */ | ||
| 541 | p_dev->resource[0]->end = p_dev->resource[1]->end = 0; | ||
| 542 | if ((cfg->io.nwin > 0) || (dflt->io.nwin > 0)) { | ||
| 543 | cistpl_io_t *io = (cfg->io.nwin) ? &cfg->io : &dflt->io; | ||
| 544 | p_dev->io_lines = io->flags & CISTPL_IO_LINES_MASK; | ||
| 545 | p_dev->resource[0]->flags &= ~IO_DATA_PATH_WIDTH; | ||
| 546 | p_dev->resource[0]->flags |= | ||
| 547 | pcmcia_io_cfg_data_width(io->flags); | ||
| 548 | p_dev->resource[0]->start = io->win[0].base; | ||
| 549 | p_dev->resource[0]->end = io->win[0].len; | ||
| 550 | if (io->nwin > 1) { | ||
| 551 | p_dev->resource[1]->flags = p_dev->resource[0]->flags; | ||
| 552 | p_dev->resource[1]->start = io->win[1].base; | ||
| 553 | p_dev->resource[1]->end = io->win[1].len; | ||
| 554 | } | ||
| 555 | /* This reserves IO space but doesn't actually enable it */ | ||
| 556 | if (pcmcia_request_io(p_dev) != 0) | ||
| 557 | return -ENODEV; | ||
| 558 | } | ||
| 559 | 537 | ||
| 560 | /* If we got this far, we're cool! */ | 538 | return pcmcia_request_io(p_dev); |
| 561 | return 0; | ||
| 562 | } | 539 | } |
| 563 | 540 | ||
| 564 | static void dio700_config(struct pcmcia_device *link) | 541 | static void dio700_config(struct pcmcia_device *link) |
| @@ -570,7 +547,8 @@ static void dio700_config(struct pcmcia_device *link) | |||
| 570 | 547 | ||
| 571 | dev_dbg(&link->dev, "dio700_config\n"); | 548 | dev_dbg(&link->dev, "dio700_config\n"); |
| 572 | 549 | ||
| 573 | link->config_flags |= CONF_ENABLE_IRQ | CONF_AUTO_AUDIO; | 550 | link->config_flags |= CONF_ENABLE_IRQ | CONF_AUTO_AUDIO | |
| 551 | CONF_AUTO_SET_IO; | ||
| 574 | 552 | ||
| 575 | ret = pcmcia_loop_config(link, dio700_pcmcia_config_loop, NULL); | 553 | ret = pcmcia_loop_config(link, dio700_pcmcia_config_loop, NULL); |
| 576 | if (ret) { | 554 | if (ret) { |
diff --git a/drivers/staging/comedi/drivers/ni_daq_dio24.c b/drivers/staging/comedi/drivers/ni_daq_dio24.c index 6dc2b06064cd..4defdda2bfaf 100644 --- a/drivers/staging/comedi/drivers/ni_daq_dio24.c +++ b/drivers/staging/comedi/drivers/ni_daq_dio24.c | |||
| @@ -282,35 +282,12 @@ static void dio24_cs_detach(struct pcmcia_device *link) | |||
| 282 | ======================================================================*/ | 282 | ======================================================================*/ |
| 283 | 283 | ||
| 284 | static int dio24_pcmcia_config_loop(struct pcmcia_device *p_dev, | 284 | static int dio24_pcmcia_config_loop(struct pcmcia_device *p_dev, |
| 285 | cistpl_cftable_entry_t *cfg, | ||
| 286 | cistpl_cftable_entry_t *dflt, | ||
| 287 | void *priv_data) | 285 | void *priv_data) |
| 288 | { | 286 | { |
| 289 | if (cfg->index == 0) | 287 | if (p_dev->config_index == 0) |
| 290 | return -ENODEV; | 288 | return -EINVAL; |
| 291 | |||
| 292 | /* IO window settings */ | ||
| 293 | p_dev->resource[0]->end = p_dev->resource[1]->end = 0; | ||
| 294 | if ((cfg->io.nwin > 0) || (dflt->io.nwin > 0)) { | ||
| 295 | cistpl_io_t *io = (cfg->io.nwin) ? &cfg->io : &dflt->io; | ||
| 296 | p_dev->io_lines = io->flags & CISTPL_IO_LINES_MASK; | ||
| 297 | p_dev->resource[0]->flags &= ~IO_DATA_PATH_WIDTH; | ||
| 298 | p_dev->resource[0]->flags |= | ||
| 299 | pcmcia_io_cfg_data_width(io->flags); | ||
| 300 | p_dev->resource[0]->start = io->win[0].base; | ||
| 301 | p_dev->resource[0]->end = io->win[0].len; | ||
| 302 | if (io->nwin > 1) { | ||
| 303 | p_dev->resource[1]->flags = p_dev->resource[0]->flags; | ||
| 304 | p_dev->resource[1]->start = io->win[1].base; | ||
| 305 | p_dev->resource[1]->end = io->win[1].len; | ||
| 306 | } | ||
| 307 | /* This reserves IO space but doesn't actually enable it */ | ||
| 308 | if (pcmcia_request_io(p_dev) != 0) | ||
| 309 | return -ENODEV; | ||
| 310 | } | ||
| 311 | 289 | ||
| 312 | /* If we got this far, we're cool! */ | 290 | return pcmcia_request_io(p_dev); |
| 313 | return 0; | ||
| 314 | } | 291 | } |
| 315 | 292 | ||
| 316 | static void dio24_config(struct pcmcia_device *link) | 293 | static void dio24_config(struct pcmcia_device *link) |
| @@ -321,7 +298,8 @@ static void dio24_config(struct pcmcia_device *link) | |||
| 321 | 298 | ||
| 322 | dev_dbg(&link->dev, "dio24_config\n"); | 299 | dev_dbg(&link->dev, "dio24_config\n"); |
| 323 | 300 | ||
| 324 | link->config_flags |= CONF_ENABLE_IRQ | CONF_AUTO_AUDIO; | 301 | link->config_flags |= CONF_ENABLE_IRQ | CONF_AUTO_AUDIO | |
| 302 | CONF_AUTO_SET_IO; | ||
| 325 | 303 | ||
| 326 | ret = pcmcia_loop_config(link, dio24_pcmcia_config_loop, NULL); | 304 | ret = pcmcia_loop_config(link, dio24_pcmcia_config_loop, NULL); |
| 327 | if (ret) { | 305 | if (ret) { |
diff --git a/drivers/staging/comedi/drivers/ni_labpc_cs.c b/drivers/staging/comedi/drivers/ni_labpc_cs.c index 6eacbd70e2e9..5123b3131c51 100644 --- a/drivers/staging/comedi/drivers/ni_labpc_cs.c +++ b/drivers/staging/comedi/drivers/ni_labpc_cs.c | |||
| @@ -261,35 +261,12 @@ static void labpc_cs_detach(struct pcmcia_device *link) | |||
| 261 | ======================================================================*/ | 261 | ======================================================================*/ |
| 262 | 262 | ||
| 263 | static int labpc_pcmcia_config_loop(struct pcmcia_device *p_dev, | 263 | static int labpc_pcmcia_config_loop(struct pcmcia_device *p_dev, |
| 264 | cistpl_cftable_entry_t *cfg, | ||
| 265 | cistpl_cftable_entry_t *dflt, | ||
| 266 | void *priv_data) | 264 | void *priv_data) |
| 267 | { | 265 | { |
| 268 | if (cfg->index == 0) | 266 | if (p_dev->config_index == 0) |
| 269 | return -ENODEV; | 267 | return -EINVAL; |
| 270 | |||
| 271 | /* IO window settings */ | ||
| 272 | p_dev->resource[0]->end = p_dev->resource[1]->end = 0; | ||
| 273 | if ((cfg->io.nwin > 0) || (dflt->io.nwin > 0)) { | ||
| 274 | cistpl_io_t *io = (cfg->io.nwin) ? &cfg->io : &dflt->io; | ||
| 275 | p_dev->io_lines = io->flags & CISTPL_IO_LINES_MASK; | ||
| 276 | p_dev->resource[0]->flags &= ~IO_DATA_PATH_WIDTH; | ||
| 277 | p_dev->resource[0]->flags |= | ||
| 278 | pcmcia_io_cfg_data_width(io->flags); | ||
| 279 | p_dev->resource[0]->start = io->win[0].base; | ||
| 280 | p_dev->resource[0]->end = io->win[0].len; | ||
| 281 | if (io->nwin > 1) { | ||
| 282 | p_dev->resource[1]->flags = p_dev->resource[0]->flags; | ||
| 283 | p_dev->resource[1]->start = io->win[1].base; | ||
| 284 | p_dev->resource[1]->end = io->win[1].len; | ||
| 285 | } | ||
| 286 | /* This reserves IO space but doesn't actually enable it */ | ||
| 287 | if (pcmcia_request_io(p_dev) != 0) | ||
| 288 | return -ENODEV; | ||
| 289 | } | ||
| 290 | 268 | ||
| 291 | /* If we got this far, we're cool! */ | 269 | return pcmcia_request_io(p_dev); |
| 292 | return 0; | ||
| 293 | } | 270 | } |
| 294 | 271 | ||
| 295 | 272 | ||
| @@ -300,7 +277,7 @@ static void labpc_config(struct pcmcia_device *link) | |||
| 300 | dev_dbg(&link->dev, "labpc_config\n"); | 277 | dev_dbg(&link->dev, "labpc_config\n"); |
| 301 | 278 | ||
| 302 | link->config_flags |= CONF_ENABLE_IRQ | CONF_ENABLE_PULSE_IRQ | | 279 | link->config_flags |= CONF_ENABLE_IRQ | CONF_ENABLE_PULSE_IRQ | |
| 303 | CONF_AUTO_AUDIO; | 280 | CONF_AUTO_AUDIO | CONF_AUTO_SET_IO; |
| 304 | 281 | ||
| 305 | ret = pcmcia_loop_config(link, labpc_pcmcia_config_loop, NULL); | 282 | ret = pcmcia_loop_config(link, labpc_pcmcia_config_loop, NULL); |
| 306 | if (ret) { | 283 | if (ret) { |
| @@ -316,7 +293,6 @@ static void labpc_config(struct pcmcia_device *link) | |||
| 316 | the I/O windows and the interrupt mapping, and putting the | 293 | the I/O windows and the interrupt mapping, and putting the |
| 317 | card and host interface into "Memory and IO" mode. | 294 | card and host interface into "Memory and IO" mode. |
| 318 | */ | 295 | */ |
| 319 | p_dev->config_flags |= CONF_ENABLE_IRQ | CONF_ENABLE_PULSE_IRQ; | ||
| 320 | ret = pcmcia_enable_device(link); | 296 | ret = pcmcia_enable_device(link); |
| 321 | if (ret) | 297 | if (ret) |
| 322 | goto failed; | 298 | goto failed; |
diff --git a/drivers/staging/comedi/drivers/ni_mio_cs.c b/drivers/staging/comedi/drivers/ni_mio_cs.c index da4e2a21b19a..f1e31d3e12bc 100644 --- a/drivers/staging/comedi/drivers/ni_mio_cs.c +++ b/drivers/staging/comedi/drivers/ni_mio_cs.c | |||
| @@ -262,10 +262,6 @@ static struct pcmcia_device *cur_dev = NULL; | |||
| 262 | 262 | ||
| 263 | static int cs_attach(struct pcmcia_device *link) | 263 | static int cs_attach(struct pcmcia_device *link) |
| 264 | { | 264 | { |
| 265 | link->resource[0]->flags |= IO_DATA_PATH_WIDTH_16; | ||
| 266 | link->resource[0]->end = 16; | ||
| 267 | link->config_flags |= CONF_ENABLE_IRQ; | ||
| 268 | |||
| 269 | cur_dev = link; | 265 | cur_dev = link; |
| 270 | 266 | ||
| 271 | mio_cs_config(link); | 267 | mio_cs_config(link); |
| @@ -299,15 +295,12 @@ static int mio_cs_resume(struct pcmcia_device *link) | |||
| 299 | } | 295 | } |
| 300 | 296 | ||
| 301 | 297 | ||
| 302 | static int mio_pcmcia_config_loop(struct pcmcia_device *p_dev, | 298 | static int mio_pcmcia_config_loop(struct pcmcia_device *p_dev, void *priv_data) |
| 303 | cistpl_cftable_entry_t *cfg, | ||
| 304 | cistpl_cftable_entry_t *dflt, | ||
| 305 | void *priv_data) | ||
| 306 | { | 299 | { |
| 307 | int base, ret; | 300 | int base, ret; |
| 308 | 301 | ||
| 309 | p_dev->resource[0]->end = cfg->io.win[0].len; | 302 | p_dev->resource[0]->flags &= ~IO_DATA_PATH_WIDTH; |
| 310 | p_dev->io_lines = cfg->io.flags & CISTPL_IO_LINES_MASK; | 303 | p_dev->resource[0]->flags |= IO_DATA_PATH_WIDTH_16; |
| 311 | 304 | ||
| 312 | for (base = 0x000; base < 0x400; base += 0x20) { | 305 | for (base = 0x000; base < 0x400; base += 0x20) { |
| 313 | p_dev->resource[0]->start = base; | 306 | p_dev->resource[0]->start = base; |
| @@ -324,6 +317,7 @@ static void mio_cs_config(struct pcmcia_device *link) | |||
| 324 | int ret; | 317 | int ret; |
| 325 | 318 | ||
| 326 | DPRINTK("mio_cs_config(link=%p)\n", link); | 319 | DPRINTK("mio_cs_config(link=%p)\n", link); |
| 320 | link->config_flags |= CONF_ENABLE_IRQ | CONF_AUTO_SET_IO; | ||
| 327 | 321 | ||
| 328 | ret = pcmcia_loop_config(link, mio_pcmcia_config_loop, NULL); | 322 | ret = pcmcia_loop_config(link, mio_pcmcia_config_loop, NULL); |
| 329 | if (ret) { | 323 | if (ret) { |
diff --git a/drivers/staging/comedi/drivers/quatech_daqp_cs.c b/drivers/staging/comedi/drivers/quatech_daqp_cs.c index 03a72d7ac676..afd283d0e711 100644 --- a/drivers/staging/comedi/drivers/quatech_daqp_cs.c +++ b/drivers/staging/comedi/drivers/quatech_daqp_cs.c | |||
| @@ -1068,35 +1068,11 @@ static void daqp_cs_detach(struct pcmcia_device *link) | |||
| 1068 | ======================================================================*/ | 1068 | ======================================================================*/ |
| 1069 | 1069 | ||
| 1070 | 1070 | ||
| 1071 | static int daqp_pcmcia_config_loop(struct pcmcia_device *p_dev, | 1071 | static int daqp_pcmcia_config_loop(struct pcmcia_device *p_dev, void *priv_data) |
| 1072 | cistpl_cftable_entry_t *cfg, | ||
| 1073 | cistpl_cftable_entry_t *dflt, | ||
| 1074 | void *priv_data) | ||
| 1075 | { | 1072 | { |
| 1076 | if (cfg->index == 0) | 1073 | if (p_dev->config_index == 0) |
| 1077 | return -ENODEV; | 1074 | return -EINVAL; |
| 1078 | 1075 | ||
| 1079 | /* Do we need to allocate an interrupt? */ | ||
| 1080 | p_dev->config_flags |= CONF_ENABLE_IRQ; | ||
| 1081 | |||
| 1082 | /* IO window settings */ | ||
| 1083 | p_dev->resource[0]->end = p_dev->resource[1]->end = 0; | ||
| 1084 | if ((cfg->io.nwin > 0) || (dflt->io.nwin > 0)) { | ||
| 1085 | cistpl_io_t *io = (cfg->io.nwin) ? &cfg->io : &dflt->io; | ||
| 1086 | p_dev->io_lines = io->flags & CISTPL_IO_LINES_MASK; | ||
| 1087 | p_dev->resource[0]->flags &= ~IO_DATA_PATH_WIDTH; | ||
| 1088 | p_dev->resource[0]->flags |= | ||
| 1089 | pcmcia_io_cfg_data_width(io->flags); | ||
| 1090 | p_dev->resource[0]->start = io->win[0].base; | ||
| 1091 | p_dev->resource[0]->end = io->win[0].len; | ||
| 1092 | if (io->nwin > 1) { | ||
| 1093 | p_dev->resource[1]->flags = p_dev->resource[0]->flags; | ||
| 1094 | p_dev->resource[1]->start = io->win[1].base; | ||
| 1095 | p_dev->resource[1]->end = io->win[1].len; | ||
| 1096 | } | ||
| 1097 | } | ||
| 1098 | |||
| 1099 | /* This reserves IO space but doesn't actually enable it */ | ||
| 1100 | return pcmcia_request_io(p_dev); | 1076 | return pcmcia_request_io(p_dev); |
| 1101 | } | 1077 | } |
| 1102 | 1078 | ||
| @@ -1106,6 +1082,8 @@ static void daqp_cs_config(struct pcmcia_device *link) | |||
| 1106 | 1082 | ||
| 1107 | dev_dbg(&link->dev, "daqp_cs_config\n"); | 1083 | dev_dbg(&link->dev, "daqp_cs_config\n"); |
| 1108 | 1084 | ||
| 1085 | link->config_flags |= CONF_ENABLE_IRQ | CONF_AUTO_SET_IO; | ||
| 1086 | |||
| 1109 | ret = pcmcia_loop_config(link, daqp_pcmcia_config_loop, NULL); | 1087 | ret = pcmcia_loop_config(link, daqp_pcmcia_config_loop, NULL); |
| 1110 | if (ret) { | 1088 | if (ret) { |
| 1111 | dev_warn(&link->dev, "no configuration found\n"); | 1089 | dev_warn(&link->dev, "no configuration found\n"); |
diff --git a/drivers/telephony/ixj_pcmcia.c b/drivers/telephony/ixj_pcmcia.c index 670a76bf5164..76edd39525de 100644 --- a/drivers/telephony/ixj_pcmcia.c +++ b/drivers/telephony/ixj_pcmcia.c | |||
| @@ -31,8 +31,6 @@ static int ixj_probe(struct pcmcia_device *p_dev) | |||
| 31 | { | 31 | { |
| 32 | dev_dbg(&p_dev->dev, "ixj_attach()\n"); | 32 | dev_dbg(&p_dev->dev, "ixj_attach()\n"); |
| 33 | /* Create new ixj device */ | 33 | /* Create new ixj device */ |
| 34 | p_dev->resource[0]->flags |= IO_DATA_PATH_WIDTH_8; | ||
| 35 | p_dev->resource[1]->flags |= IO_DATA_PATH_WIDTH_8; | ||
| 36 | p_dev->priv = kzalloc(sizeof(struct ixj_info_t), GFP_KERNEL); | 34 | p_dev->priv = kzalloc(sizeof(struct ixj_info_t), GFP_KERNEL); |
| 37 | if (!p_dev->priv) { | 35 | if (!p_dev->priv) { |
| 38 | return -ENOMEM; | 36 | return -ENOMEM; |
| @@ -109,36 +107,28 @@ failed: | |||
| 109 | return; | 107 | return; |
| 110 | } | 108 | } |
| 111 | 109 | ||
| 112 | static int ixj_config_check(struct pcmcia_device *p_dev, | 110 | static int ixj_config_check(struct pcmcia_device *p_dev, void *priv_data) |
| 113 | cistpl_cftable_entry_t *cfg, | ||
| 114 | cistpl_cftable_entry_t *dflt, | ||
| 115 | void *priv_data) | ||
| 116 | { | 111 | { |
| 117 | if ((cfg->io.nwin > 0) || (dflt->io.nwin > 0)) { | 112 | p_dev->resource[0]->flags &= ~IO_DATA_PATH_WIDTH; |
| 118 | cistpl_io_t *io = (cfg->io.nwin) ? &cfg->io : &dflt->io; | 113 | p_dev->resource[0]->flags |= IO_DATA_PATH_WIDTH_8; |
| 119 | p_dev->resource[0]->start = io->win[0].base; | 114 | p_dev->resource[1]->flags &= ~IO_DATA_PATH_WIDTH; |
| 120 | p_dev->resource[0]->end = io->win[0].len; | 115 | p_dev->resource[1]->flags |= IO_DATA_PATH_WIDTH_8; |
| 121 | p_dev->io_lines = 3; | 116 | p_dev->io_lines = 3; |
| 122 | if (io->nwin == 2) { | 117 | |
| 123 | p_dev->resource[1]->start = io->win[1].base; | 118 | return pcmcia_request_io(p_dev); |
| 124 | p_dev->resource[1]->end = io->win[1].len; | ||
| 125 | } | ||
| 126 | if (!pcmcia_request_io(p_dev)) | ||
| 127 | return 0; | ||
| 128 | } | ||
| 129 | return -ENODEV; | ||
| 130 | } | 119 | } |
| 131 | 120 | ||
| 132 | static int ixj_config(struct pcmcia_device * link) | 121 | static int ixj_config(struct pcmcia_device * link) |
| 133 | { | 122 | { |
| 134 | IXJ *j; | 123 | IXJ *j; |
| 135 | ixj_info_t *info; | 124 | ixj_info_t *info; |
| 136 | cistpl_cftable_entry_t dflt = { 0 }; | ||
| 137 | 125 | ||
| 138 | info = link->priv; | 126 | info = link->priv; |
| 139 | dev_dbg(&link->dev, "ixj_config\n"); | 127 | dev_dbg(&link->dev, "ixj_config\n"); |
| 140 | 128 | ||
| 141 | if (pcmcia_loop_config(link, ixj_config_check, &dflt)) | 129 | link->config_flags = CONF_AUTO_SET_IO; |
| 130 | |||
| 131 | if (pcmcia_loop_config(link, ixj_config_check, NULL)) | ||
| 142 | goto failed; | 132 | goto failed; |
| 143 | 133 | ||
| 144 | if (pcmcia_enable_device(link)) | 134 | if (pcmcia_enable_device(link)) |
diff --git a/drivers/usb/host/sl811_cs.c b/drivers/usb/host/sl811_cs.c index d9606293c1af..81d7eeacdf6a 100644 --- a/drivers/usb/host/sl811_cs.c +++ b/drivers/usb/host/sl811_cs.c | |||
| @@ -131,28 +131,12 @@ static void sl811_cs_release(struct pcmcia_device * link) | |||
| 131 | platform_device_unregister(&platform_dev); | 131 | platform_device_unregister(&platform_dev); |
| 132 | } | 132 | } |
| 133 | 133 | ||
| 134 | static int sl811_cs_config_check(struct pcmcia_device *p_dev, | 134 | static int sl811_cs_config_check(struct pcmcia_device *p_dev, void *priv_data) |
| 135 | cistpl_cftable_entry_t *cfg, | ||
| 136 | cistpl_cftable_entry_t *dflt, | ||
| 137 | void *priv_data) | ||
| 138 | { | 135 | { |
| 139 | if (cfg->index == 0) | 136 | if (p_dev->config_index == 0) |
| 140 | return -ENODEV; | 137 | return -EINVAL; |
| 141 | 138 | ||
| 142 | /* IO window settings */ | 139 | return pcmcia_request_io(p_dev); |
| 143 | p_dev->resource[0]->end = p_dev->resource[1]->end = 0; | ||
| 144 | if ((cfg->io.nwin > 0) || (dflt->io.nwin > 0)) { | ||
| 145 | cistpl_io_t *io = (cfg->io.nwin) ? &cfg->io : &dflt->io; | ||
| 146 | p_dev->io_lines = io->flags & CISTPL_IO_LINES_MASK; | ||
| 147 | |||
| 148 | p_dev->resource[0]->flags |= IO_DATA_PATH_WIDTH_8; | ||
| 149 | p_dev->resource[0]->start = io->win[0].base; | ||
| 150 | p_dev->resource[0]->end = io->win[0].len; | ||
| 151 | |||
| 152 | return pcmcia_request_io(p_dev); | ||
| 153 | } | ||
| 154 | pcmcia_disable_device(p_dev); | ||
| 155 | return -ENODEV; | ||
| 156 | } | 140 | } |
| 157 | 141 | ||
| 158 | 142 | ||
| @@ -164,7 +148,7 @@ static int sl811_cs_config(struct pcmcia_device *link) | |||
| 164 | dev_dbg(&link->dev, "sl811_cs_config\n"); | 148 | dev_dbg(&link->dev, "sl811_cs_config\n"); |
| 165 | 149 | ||
| 166 | link->config_flags |= CONF_ENABLE_IRQ | CONF_AUTO_SET_VPP | | 150 | link->config_flags |= CONF_ENABLE_IRQ | CONF_AUTO_SET_VPP | |
| 167 | CONF_AUTO_CHECK_VCC; | 151 | CONF_AUTO_CHECK_VCC | CONF_AUTO_SET_IO; |
| 168 | 152 | ||
| 169 | if (pcmcia_loop_config(link, sl811_cs_config_check, NULL)) | 153 | if (pcmcia_loop_config(link, sl811_cs_config_check, NULL)) |
| 170 | goto failed; | 154 | goto failed; |
diff --git a/include/pcmcia/ds.h b/include/pcmcia/ds.h index 0577e5f10304..0b8c8d45df47 100644 --- a/include/pcmcia/ds.h +++ b/include/pcmcia/ds.h | |||
| @@ -93,6 +93,7 @@ struct pcmcia_device { | |||
| 93 | /* device setup */ | 93 | /* device setup */ |
| 94 | unsigned int irq; | 94 | unsigned int irq; |
| 95 | struct resource *resource[PCMCIA_NUM_RESOURCES]; | 95 | struct resource *resource[PCMCIA_NUM_RESOURCES]; |
| 96 | resource_size_t card_addr; /* for the 1st IOMEM resource */ | ||
| 96 | unsigned int vpp; | 97 | unsigned int vpp; |
| 97 | 98 | ||
| 98 | unsigned int config_flags; /* CONF_ENABLE_ flags below */ | 99 | unsigned int config_flags; /* CONF_ENABLE_ flags below */ |
| @@ -175,8 +176,6 @@ int pcmcia_parse_tuple(tuple_t *tuple, cisparse_t *parse); | |||
| 175 | /* loop CIS entries for valid configuration */ | 176 | /* loop CIS entries for valid configuration */ |
| 176 | int pcmcia_loop_config(struct pcmcia_device *p_dev, | 177 | int pcmcia_loop_config(struct pcmcia_device *p_dev, |
| 177 | int (*conf_check) (struct pcmcia_device *p_dev, | 178 | int (*conf_check) (struct pcmcia_device *p_dev, |
| 178 | cistpl_cftable_entry_t *cf, | ||
| 179 | cistpl_cftable_entry_t *dflt, | ||
| 180 | void *priv_data), | 179 | void *priv_data), |
| 181 | void *priv_data); | 180 | void *priv_data); |
| 182 | 181 | ||
| @@ -225,16 +224,6 @@ void pcmcia_disable_device(struct pcmcia_device *p_dev); | |||
| 225 | #define IO_DATA_PATH_WIDTH_16 0x08 | 224 | #define IO_DATA_PATH_WIDTH_16 0x08 |
| 226 | #define IO_DATA_PATH_WIDTH_AUTO 0x10 | 225 | #define IO_DATA_PATH_WIDTH_AUTO 0x10 |
| 227 | 226 | ||
| 228 | /* convert flag found in cfgtable to data path width parameter */ | ||
| 229 | static inline int pcmcia_io_cfg_data_width(unsigned int flags) | ||
| 230 | { | ||
| 231 | if (!(flags & CISTPL_IO_8BIT)) | ||
| 232 | return IO_DATA_PATH_WIDTH_16; | ||
| 233 | if (!(flags & CISTPL_IO_16BIT)) | ||
| 234 | return IO_DATA_PATH_WIDTH_8; | ||
| 235 | return IO_DATA_PATH_WIDTH_AUTO; | ||
| 236 | } | ||
| 237 | |||
| 238 | /* IO memory */ | 227 | /* IO memory */ |
| 239 | #define WIN_MEMORY_TYPE_CM 0x00 /* default */ | 228 | #define WIN_MEMORY_TYPE_CM 0x00 /* default */ |
| 240 | #define WIN_MEMORY_TYPE_AM 0x20 /* MAP_ATTRIB */ | 229 | #define WIN_MEMORY_TYPE_AM 0x20 /* MAP_ATTRIB */ |
| @@ -264,16 +253,17 @@ static inline int pcmcia_io_cfg_data_width(unsigned int flags) | |||
| 264 | #define PRESENT_IOSIZE 0x200 | 253 | #define PRESENT_IOSIZE 0x200 |
| 265 | 254 | ||
| 266 | /* flags to be passed to pcmcia_enable_device() */ | 255 | /* flags to be passed to pcmcia_enable_device() */ |
| 267 | #define CONF_ENABLE_IRQ 0x01 | 256 | #define CONF_ENABLE_IRQ 0x0001 |
| 268 | #define CONF_ENABLE_SPKR 0x02 | 257 | #define CONF_ENABLE_SPKR 0x0002 |
| 269 | #define CONF_ENABLE_PULSE_IRQ 0x04 | 258 | #define CONF_ENABLE_PULSE_IRQ 0x0004 |
| 270 | #define CONF_ENABLE_ESR 0x08 | 259 | #define CONF_ENABLE_ESR 0x0008 |
| 271 | 260 | ||
| 272 | /* flags used by pcmcia_loop_config() autoconfiguration */ | 261 | /* flags used by pcmcia_loop_config() autoconfiguration */ |
| 273 | #define CONF_AUTO_CHECK_VCC 0x10 /* check for matching Vcc? */ | 262 | #define CONF_AUTO_CHECK_VCC 0x0100 /* check for matching Vcc? */ |
| 274 | #define CONF_AUTO_SET_VPP 0x20 /* set Vpp? */ | 263 | #define CONF_AUTO_SET_VPP 0x0200 /* set Vpp? */ |
| 275 | #define CONF_AUTO_AUDIO 0x40 /* enable audio line? */ | 264 | #define CONF_AUTO_AUDIO 0x0400 /* enable audio line? */ |
| 276 | 265 | #define CONF_AUTO_SET_IO 0x0800 /* set ->resource[0,1] */ | |
| 266 | #define CONF_AUTO_SET_IOMEM 0x1000 /* set ->resource[2] */ | ||
| 277 | 267 | ||
| 278 | #endif /* __KERNEL__ */ | 268 | #endif /* __KERNEL__ */ |
| 279 | 269 | ||
