Commit 0e6f9d27 authored by Dominik Brodowski's avatar Dominik Brodowski

pcmcia: use pcmcia_loop_config in scsi pcmcia drivers

Use the config loop helper in scsi pcmcia drivers.

CC: James E.J. Bottomley <James.Bottomley@HansenPartnership.com>
CC: linux-scsi@vger.kernel.org
Signed-off-by: default avatarDominik Brodowski <linux@dominikbrodowski.net>
parent ed58872a
...@@ -140,44 +140,40 @@ static void aha152x_detach(struct pcmcia_device *link) ...@@ -140,44 +140,40 @@ static void aha152x_detach(struct pcmcia_device *link)
#define CS_CHECK(fn, ret) \ #define CS_CHECK(fn, ret) \
do { last_fn = (fn); if ((last_ret = (ret)) != 0) goto cs_failed; } while (0) do { last_fn = (fn); if ((last_ret = (ret)) != 0) goto cs_failed; } while (0)
static int aha152x_config_check(struct pcmcia_device *p_dev,
cistpl_cftable_entry_t *cfg,
void *priv_data)
{
/* For New Media T&J, look for a SCSI window */
if (cfg->io.win[0].len >= 0x20)
p_dev->io.BasePort1 = cfg->io.win[0].base;
else if ((cfg->io.nwin > 1) &&
(cfg->io.win[1].len >= 0x20))
p_dev->io.BasePort1 = cfg->io.win[1].base;
if ((cfg->io.nwin > 0) &&
(p_dev->io.BasePort1 < 0xffff)) {
p_dev->conf.ConfigIndex = cfg->index;
if (!pcmcia_request_io(p_dev, &p_dev->io))
return 0;
}
return -EINVAL;
}
static int aha152x_config_cs(struct pcmcia_device *link) static int aha152x_config_cs(struct pcmcia_device *link)
{ {
scsi_info_t *info = link->priv; scsi_info_t *info = link->priv;
struct aha152x_setup s; struct aha152x_setup s;
tuple_t tuple; int last_ret, last_fn;
cisparse_t parse;
int i, last_ret, last_fn;
u_char tuple_data[64];
struct Scsi_Host *host; struct Scsi_Host *host;
DEBUG(0, "aha152x_config(0x%p)\n", link); DEBUG(0, "aha152x_config(0x%p)\n", link);
tuple.TupleData = tuple_data; last_ret = pcmcia_loop_config(link, aha152x_config_check, NULL);
tuple.TupleDataMax = 64; if (last_ret) {
tuple.TupleOffset = 0; cs_error(link, RequestIO, last_ret);
tuple.DesiredTuple = CISTPL_CFTABLE_ENTRY; goto failed;
tuple.Attributes = 0;
CS_CHECK(GetFirstTuple, pcmcia_get_first_tuple(link, &tuple));
while (1) {
if (pcmcia_get_tuple_data(link, &tuple) != 0 ||
pcmcia_parse_tuple(link, &tuple, &parse) != 0)
goto next_entry;
/* For New Media T&J, look for a SCSI window */
if (parse.cftable_entry.io.win[0].len >= 0x20)
link->io.BasePort1 = parse.cftable_entry.io.win[0].base;
else if ((parse.cftable_entry.io.nwin > 1) &&
(parse.cftable_entry.io.win[1].len >= 0x20))
link->io.BasePort1 = parse.cftable_entry.io.win[1].base;
if ((parse.cftable_entry.io.nwin > 0) &&
(link->io.BasePort1 < 0xffff)) {
link->conf.ConfigIndex = parse.cftable_entry.index;
i = pcmcia_request_io(link, &link->io);
if (i == CS_SUCCESS) break;
}
next_entry:
CS_CHECK(GetNextTuple, pcmcia_get_next_tuple(link, &tuple));
} }
CS_CHECK(RequestIRQ, pcmcia_request_irq(link, &link->irq)); CS_CHECK(RequestIRQ, pcmcia_request_irq(link, &link->irq));
CS_CHECK(RequestConfiguration, pcmcia_request_configuration(link, &link->conf)); CS_CHECK(RequestConfiguration, pcmcia_request_configuration(link, &link->conf));
...@@ -208,6 +204,7 @@ static int aha152x_config_cs(struct pcmcia_device *link) ...@@ -208,6 +204,7 @@ static int aha152x_config_cs(struct pcmcia_device *link)
cs_failed: cs_failed:
cs_error(link, last_fn, last_ret); cs_error(link, last_fn, last_ret);
failed:
aha152x_release_cs(link); aha152x_release_cs(link);
return -ENODEV; return -ENODEV;
} }
......
...@@ -123,34 +123,29 @@ static void fdomain_detach(struct pcmcia_device *link) ...@@ -123,34 +123,29 @@ static void fdomain_detach(struct pcmcia_device *link)
#define CS_CHECK(fn, ret) \ #define CS_CHECK(fn, ret) \
do { last_fn = (fn); if ((last_ret = (ret)) != 0) goto cs_failed; } while (0) do { last_fn = (fn); if ((last_ret = (ret)) != 0) goto cs_failed; } while (0)
static int fdomain_config_check(struct pcmcia_device *p_dev,
cistpl_cftable_entry_t *cfg,
void *priv_data)
{
p_dev->conf.ConfigIndex = cfg->index;
p_dev->io.BasePort1 = cfg->io.win[0].base;
return pcmcia_request_io(p_dev, &p_dev->io);
}
static int fdomain_config(struct pcmcia_device *link) static int fdomain_config(struct pcmcia_device *link)
{ {
scsi_info_t *info = link->priv; scsi_info_t *info = link->priv;
tuple_t tuple; int last_ret, last_fn;
cisparse_t parse;
int i, last_ret, last_fn;
u_char tuple_data[64];
char str[22]; char str[22];
struct Scsi_Host *host; struct Scsi_Host *host;
DEBUG(0, "fdomain_config(0x%p)\n", link); DEBUG(0, "fdomain_config(0x%p)\n", link);
tuple.TupleData = tuple_data; last_ret = pcmcia_loop_config(link, fdomain_config_check, NULL);
tuple.TupleDataMax = 64; if (last_ret) {
tuple.TupleOffset = 0; cs_error(link, RequestIO, last_ret);
goto failed;
tuple.DesiredTuple = CISTPL_CFTABLE_ENTRY;
CS_CHECK(GetFirstTuple, pcmcia_get_first_tuple(link, &tuple));
while (1) {
if (pcmcia_get_tuple_data(link, &tuple) != 0 ||
pcmcia_parse_tuple(link, &tuple, &parse) != 0)
goto next_entry;
link->conf.ConfigIndex = parse.cftable_entry.index;
link->io.BasePort1 = parse.cftable_entry.io.win[0].base;
i = pcmcia_request_io(link, &link->io);
if (i == CS_SUCCESS) break;
next_entry:
CS_CHECK(GetNextTuple, pcmcia_get_next_tuple(link, &tuple));
} }
CS_CHECK(RequestIRQ, pcmcia_request_irq(link, &link->irq)); CS_CHECK(RequestIRQ, pcmcia_request_irq(link, &link->irq));
...@@ -181,6 +176,7 @@ static int fdomain_config(struct pcmcia_device *link) ...@@ -181,6 +176,7 @@ static int fdomain_config(struct pcmcia_device *link)
cs_failed: cs_failed:
cs_error(link, last_fn, last_ret); cs_error(link, last_fn, last_ret);
failed:
fdomain_release(link); fdomain_release(link);
return -ENODEV; return -ENODEV;
} /* fdomain_config */ } /* fdomain_config */
......
...@@ -1607,133 +1607,136 @@ static void nsp_cs_detach(struct pcmcia_device *link) ...@@ -1607,133 +1607,136 @@ static void nsp_cs_detach(struct pcmcia_device *link)
is received, to configure the PCMCIA socket, and to make the is received, to configure the PCMCIA socket, and to make the
ethernet device available to the system. ethernet device available to the system.
======================================================================*/ ======================================================================*/
#define CS_CHECK(fn, ret) \
do { last_fn = (fn); if ((last_ret = (ret)) != 0) goto cs_failed; } while (0)
/*====================================================================*/
static int nsp_cs_config(struct pcmcia_device *link)
{
int ret;
scsi_info_t *info = link->priv;
tuple_t tuple;
cisparse_t parse;
int last_ret, last_fn;
unsigned char tuple_data[64];
config_info_t conf;
win_req_t req;
memreq_t map;
cistpl_cftable_entry_t dflt = { 0 };
struct Scsi_Host *host;
nsp_hw_data *data = &nsp_data_base;
nsp_dbg(NSP_DEBUG_INIT, "in");
tuple.Attributes = 0; struct nsp_cs_configdata {
tuple.TupleData = tuple_data; nsp_hw_data *data;
tuple.TupleDataMax = sizeof(tuple_data); win_req_t req;
tuple.TupleOffset = 0; config_info_t conf;
cistpl_cftable_entry_t dflt;
/* Look up the current Vcc */ };
CS_CHECK(GetConfigurationInfo, pcmcia_get_configuration_info(link, &conf));
tuple.DesiredTuple = CISTPL_CFTABLE_ENTRY; static int nsp_cs_config_check(struct pcmcia_device *p_dev,
CS_CHECK(GetFirstTuple, pcmcia_get_first_tuple(link, &tuple)); cistpl_cftable_entry_t *cfg,
while (1) { void *priv_data)
cistpl_cftable_entry_t *cfg = &(parse.cftable_entry); {
struct nsp_cs_configdata *cfg_mem = priv_data;
if (pcmcia_get_tuple_data(link, &tuple) != 0 || if (cfg->flags & CISTPL_CFTABLE_DEFAULT)
pcmcia_parse_tuple(link, &tuple, &parse) != 0) memcpy(&cfg_mem->dflt, cfg, sizeof(cistpl_cftable_entry_t));
goto next_entry; if (cfg->index == 0)
return -ENODEV;
if (cfg->flags & CISTPL_CFTABLE_DEFAULT) { dflt = *cfg; } p_dev->conf.ConfigIndex = cfg->index;
if (cfg->index == 0) { goto next_entry; }
link->conf.ConfigIndex = cfg->index;
/* Does this card need audio output? */ /* Does this card need audio output? */
if (cfg->flags & CISTPL_CFTABLE_AUDIO) { if (cfg->flags & CISTPL_CFTABLE_AUDIO) {
link->conf.Attributes |= CONF_ENABLE_SPKR; p_dev->conf.Attributes |= CONF_ENABLE_SPKR;
link->conf.Status = CCSR_AUDIO_ENA; p_dev->conf.Status = CCSR_AUDIO_ENA;
} }
/* Use power settings for Vcc and Vpp if present */ /* Use power settings for Vcc and Vpp if present */
/* Note that the CIS values need to be rescaled */ /* Note that the CIS values need to be rescaled */
if (cfg->vcc.present & (1<<CISTPL_POWER_VNOM)) { if (cfg->vcc.present & (1<<CISTPL_POWER_VNOM)) {
if (conf.Vcc != cfg->vcc.param[CISTPL_POWER_VNOM]/10000) { if (cfg_mem->conf.Vcc != cfg->vcc.param[CISTPL_POWER_VNOM]/10000)
goto next_entry; return -ENODEV;
} else if (cfg_mem->dflt.vcc.present & (1<<CISTPL_POWER_VNOM)) {
} else if (dflt.vcc.present & (1<<CISTPL_POWER_VNOM)) { if (cfg_mem->conf.Vcc != cfg_mem->dflt.vcc.param[CISTPL_POWER_VNOM]/10000)
if (conf.Vcc != dflt.vcc.param[CISTPL_POWER_VNOM]/10000) { return -ENODEV;
goto next_entry;
}
} }
if (cfg->vpp1.present & (1 << CISTPL_POWER_VNOM)) { if (cfg->vpp1.present & (1 << CISTPL_POWER_VNOM)) {
link->conf.Vpp = p_dev->conf.Vpp =
cfg->vpp1.param[CISTPL_POWER_VNOM] / 10000; cfg->vpp1.param[CISTPL_POWER_VNOM] / 10000;
} else if (dflt.vpp1.present & (1 << CISTPL_POWER_VNOM)) { } else if (cfg_mem->dflt.vpp1.present & (1 << CISTPL_POWER_VNOM)) {
link->conf.Vpp = p_dev->conf.Vpp =
dflt.vpp1.param[CISTPL_POWER_VNOM] / 10000; cfg_mem->dflt.vpp1.param[CISTPL_POWER_VNOM] / 10000;
} }
/* Do we need to allocate an interrupt? */ /* Do we need to allocate an interrupt? */
if (cfg->irq.IRQInfo1 || dflt.irq.IRQInfo1) { if (cfg->irq.IRQInfo1 || cfg_mem->dflt.irq.IRQInfo1) {
link->conf.Attributes |= CONF_ENABLE_IRQ; p_dev->conf.Attributes |= CONF_ENABLE_IRQ;
} }
/* IO window settings */ /* IO window settings */
link->io.NumPorts1 = link->io.NumPorts2 = 0; p_dev->io.NumPorts1 = p_dev->io.NumPorts2 = 0;
if ((cfg->io.nwin > 0) || (dflt.io.nwin > 0)) { if ((cfg->io.nwin > 0) || (cfg_mem->dflt.io.nwin > 0)) {
cistpl_io_t *io = (cfg->io.nwin) ? &cfg->io : &dflt.io; cistpl_io_t *io = (cfg->io.nwin) ? &cfg->io : &cfg_mem->dflt.io;
link->io.Attributes1 = IO_DATA_PATH_WIDTH_AUTO; p_dev->io.Attributes1 = IO_DATA_PATH_WIDTH_AUTO;
if (!(io->flags & CISTPL_IO_8BIT)) if (!(io->flags & CISTPL_IO_8BIT))
link->io.Attributes1 = IO_DATA_PATH_WIDTH_16; p_dev->io.Attributes1 = IO_DATA_PATH_WIDTH_16;
if (!(io->flags & CISTPL_IO_16BIT)) if (!(io->flags & CISTPL_IO_16BIT))
link->io.Attributes1 = IO_DATA_PATH_WIDTH_8; p_dev->io.Attributes1 = IO_DATA_PATH_WIDTH_8;
link->io.IOAddrLines = io->flags & CISTPL_IO_LINES_MASK; p_dev->io.IOAddrLines = io->flags & CISTPL_IO_LINES_MASK;
link->io.BasePort1 = io->win[0].base; p_dev->io.BasePort1 = io->win[0].base;
link->io.NumPorts1 = io->win[0].len; p_dev->io.NumPorts1 = io->win[0].len;
if (io->nwin > 1) { if (io->nwin > 1) {
link->io.Attributes2 = link->io.Attributes1; p_dev->io.Attributes2 = p_dev->io.Attributes1;
link->io.BasePort2 = io->win[1].base; p_dev->io.BasePort2 = io->win[1].base;
link->io.NumPorts2 = io->win[1].len; p_dev->io.NumPorts2 = io->win[1].len;
} }
/* This reserves IO space but doesn't actually enable it */ /* This reserves IO space but doesn't actually enable it */
if (pcmcia_request_io(link, &link->io) != 0) if (pcmcia_request_io(p_dev, &p_dev->io) != 0)
goto next_entry; goto next_entry;
} }
if ((cfg->mem.nwin > 0) || (dflt.mem.nwin > 0)) { if ((cfg->mem.nwin > 0) || (cfg_mem->dflt.mem.nwin > 0)) {
cistpl_mem_t *mem = memreq_t map;
(cfg->mem.nwin) ? &cfg->mem : &dflt.mem; cistpl_mem_t *mem =
req.Attributes = WIN_DATA_WIDTH_16|WIN_MEMORY_TYPE_CM; (cfg->mem.nwin) ? &cfg->mem : &cfg_mem->dflt.mem;
req.Attributes |= WIN_ENABLE; cfg_mem->req.Attributes = WIN_DATA_WIDTH_16|WIN_MEMORY_TYPE_CM;
req.Base = mem->win[0].host_addr; cfg_mem->req.Attributes |= WIN_ENABLE;
req.Size = mem->win[0].len; cfg_mem->req.Base = mem->win[0].host_addr;
if (req.Size < 0x1000) { cfg_mem->req.Size = mem->win[0].len;
req.Size = 0x1000; if (cfg_mem->req.Size < 0x1000)
} cfg_mem->req.Size = 0x1000;
req.AccessSpeed = 0; cfg_mem->req.AccessSpeed = 0;
if (pcmcia_request_window(&link, &req, &link->win) != 0) if (pcmcia_request_window(&p_dev, &cfg_mem->req, &p_dev->win) != 0)
goto next_entry; goto next_entry;
map.Page = 0; map.CardOffset = mem->win[0].card_addr; map.Page = 0; map.CardOffset = mem->win[0].card_addr;
if (pcmcia_map_mem_page(link->win, &map) != 0) if (pcmcia_map_mem_page(p_dev->win, &map) != 0)
goto next_entry; goto next_entry;
data->MmioAddress = (unsigned long)ioremap_nocache(req.Base, req.Size); cfg_mem->data->MmioAddress = (unsigned long) ioremap_nocache(cfg_mem->req.Base, cfg_mem->req.Size);
data->MmioLength = req.Size; cfg_mem->data->MmioLength = cfg_mem->req.Size;
} }
/* If we got this far, we're cool! */ /* If we got this far, we're cool! */
break; return 0;
next_entry:
nsp_dbg(NSP_DEBUG_INIT, "next");
pcmcia_disable_device(link);
CS_CHECK(GetNextTuple, pcmcia_get_next_tuple(link, &tuple));
} }
next_entry:
nsp_dbg(NSP_DEBUG_INIT, "next");
pcmcia_disable_device(p_dev);
return -ENODEV;
}
static int nsp_cs_config(struct pcmcia_device *link)
{
int ret;
scsi_info_t *info = link->priv;
struct nsp_cs_configdata *cfg_mem;
struct Scsi_Host *host;
nsp_hw_data *data = &nsp_data_base;
nsp_dbg(NSP_DEBUG_INIT, "in");
cfg_mem = kzalloc(sizeof(cfg_mem), GFP_KERNEL);
if (!cfg_mem)
return -ENOMEM;
cfg_mem->data = data;
/* Look up the current Vcc */
CS_CHECK(GetConfigurationInfo, pcmcia_get_configuration_info(link, &cfg_mem->conf));
ret = pcmcia_loop_config(link, nsp_cs_config_check, cfg_mem);
goto cs_failed;
if (link->conf.Attributes & CONF_ENABLE_IRQ) { if (link->conf.Attributes & CONF_ENABLE_IRQ) {
CS_CHECK(RequestIRQ, pcmcia_request_irq(link, &link->irq)); if (pcmcia_request_irq(link, &link->irq))
goto cs_failed;
} }
CS_CHECK(RequestConfiguration, pcmcia_request_configuration(link, &link->conf));
ret = pcmcia_request_configuration(link, &link->conf);
if (ret)
goto cs_failed;
if (free_ports) { if (free_ports) {
if (link->io.BasePort1) { if (link->io.BasePort1) {
...@@ -1791,20 +1794,20 @@ static int nsp_cs_config(struct pcmcia_device *link) ...@@ -1791,20 +1794,20 @@ static int nsp_cs_config(struct pcmcia_device *link)
printk(" & 0x%04x-0x%04x", link->io.BasePort2, printk(" & 0x%04x-0x%04x", link->io.BasePort2,
link->io.BasePort2+link->io.NumPorts2-1); link->io.BasePort2+link->io.NumPorts2-1);
if (link->win) if (link->win)
printk(", mem 0x%06lx-0x%06lx", req.Base, printk(", mem 0x%06lx-0x%06lx", cfg_mem->req.Base,
req.Base+req.Size-1); cfg_mem->req.Base+cfg_mem->req.Size-1);
printk("\n"); printk("\n");
kfree(cfg_mem);
return 0; return 0;
cs_failed: cs_failed:
nsp_dbg(NSP_DEBUG_INIT, "config fail"); nsp_dbg(NSP_DEBUG_INIT, "config fail");
cs_error(link, last_fn, last_ret);
nsp_cs_release(link); nsp_cs_release(link);
kfree(cfg_mem);
return -ENODEV; return -ENODEV;
} /* nsp_cs_config */ } /* nsp_cs_config */
#undef CS_CHECK
/*====================================================================== /*======================================================================
......
...@@ -195,39 +195,32 @@ static void qlogic_detach(struct pcmcia_device *link) ...@@ -195,39 +195,32 @@ static void qlogic_detach(struct pcmcia_device *link)
#define CS_CHECK(fn, ret) \ #define CS_CHECK(fn, ret) \
do { last_fn = (fn); if ((last_ret = (ret)) != 0) goto cs_failed; } while (0) do { last_fn = (fn); if ((last_ret = (ret)) != 0) goto cs_failed; } while (0)
static int qlogic_config_check(struct pcmcia_device *p_dev,
cistpl_cftable_entry_t *cfg,
void *priv_data)
{
p_dev->conf.ConfigIndex = cfg->index;
p_dev->io.BasePort1 = cfg->io.win[0].base;
p_dev->io.NumPorts1 = cfg->io.win[0].len;
if (p_dev->io.BasePort1 == 0)
return -ENODEV;
return pcmcia_request_io(p_dev, &p_dev->io);
}
static int qlogic_config(struct pcmcia_device * link) static int qlogic_config(struct pcmcia_device * link)
{ {
scsi_info_t *info = link->priv; scsi_info_t *info = link->priv;
tuple_t tuple; int last_ret, last_fn;
cisparse_t parse;
int i, last_ret, last_fn;
unsigned short tuple_data[32];
struct Scsi_Host *host; struct Scsi_Host *host;
DEBUG(0, "qlogic_config(0x%p)\n", link); DEBUG(0, "qlogic_config(0x%p)\n", link);
info->manf_id = link->manf_id; last_ret = pcmcia_loop_config(link, qlogic_config_check, NULL);
if (last_ret) {
tuple.TupleData = (cisdata_t *) tuple_data; cs_error(link, RequestIO, last_ret);
tuple.TupleDataMax = 64; goto failed;
tuple.TupleOffset = 0;
tuple.DesiredTuple = CISTPL_CFTABLE_ENTRY;
CS_CHECK(GetFirstTuple, pcmcia_get_first_tuple(link, &tuple));
while (1) {
if (pcmcia_get_tuple_data(link, &tuple) != 0 ||
pcmcia_parse_tuple(link, &tuple, &parse) != 0)
goto next_entry;
link->conf.ConfigIndex = parse.cftable_entry.index;
link->io.BasePort1 = parse.cftable_entry.io.win[0].base;
link->io.NumPorts1 = parse.cftable_entry.io.win[0].len;
if (link->io.BasePort1 != 0) {
i = pcmcia_request_io(link, &link->io);
if (i == CS_SUCCESS)
break;
}
next_entry:
CS_CHECK(GetNextTuple, pcmcia_get_next_tuple(link, &tuple));
} }
CS_CHECK(RequestIRQ, pcmcia_request_irq(link, &link->irq)); CS_CHECK(RequestIRQ, pcmcia_request_irq(link, &link->irq));
...@@ -262,6 +255,7 @@ static int qlogic_config(struct pcmcia_device * link) ...@@ -262,6 +255,7 @@ static int qlogic_config(struct pcmcia_device * link)
cs_failed: cs_failed:
cs_error(link, last_fn, last_ret); cs_error(link, last_fn, last_ret);
pcmcia_disable_device(link); pcmcia_disable_device(link);
failed:
return -ENODEV; return -ENODEV;
} /* qlogic_config */ } /* qlogic_config */
......
...@@ -700,15 +700,26 @@ static struct scsi_host_template sym53c500_driver_template = { ...@@ -700,15 +700,26 @@ static struct scsi_host_template sym53c500_driver_template = {
#define CS_CHECK(fn, ret) \ #define CS_CHECK(fn, ret) \
do { last_fn = (fn); if ((last_ret = (ret)) != 0) goto cs_failed; } while (0) do { last_fn = (fn); if ((last_ret = (ret)) != 0) goto cs_failed; } while (0)
static int SYM53C500_config_check(struct pcmcia_device *p_dev,
cistpl_cftable_entry_t *cfg,
void *priv_data)
{
p_dev->conf.ConfigIndex = cfg->index;
p_dev->io.BasePort1 = cfg->io.win[0].base;
p_dev->io.NumPorts1 = cfg->io.win[0].len;
if (p_dev->io.BasePort1 == 0)
return -ENODEV;
return pcmcia_request_io(p_dev, &p_dev->io);
}
static int static int
SYM53C500_config(struct pcmcia_device *link) SYM53C500_config(struct pcmcia_device *link)
{ {
struct scsi_info_t *info = link->priv; struct scsi_info_t *info = link->priv;
tuple_t tuple; int last_ret, last_fn;
cisparse_t parse;
int i, last_ret, last_fn;
int irq_level, port_base; int irq_level, port_base;
unsigned short tuple_data[32];
struct Scsi_Host *host; struct Scsi_Host *host;
struct scsi_host_template *tpnt = &sym53c500_driver_template; struct scsi_host_template *tpnt = &sym53c500_driver_template;
struct sym53c500_data *data; struct sym53c500_data *data;
...@@ -717,27 +728,10 @@ SYM53C500_config(struct pcmcia_device *link) ...@@ -717,27 +728,10 @@ SYM53C500_config(struct pcmcia_device *link)
info->manf_id = link->manf_id; info->manf_id = link->manf_id;
tuple.TupleData = (cisdata_t *)tuple_data; last_ret = pcmcia_loop_config(link, SYM53C500_config_check, NULL);
tuple.TupleDataMax = 64; if (last_ret) {
tuple.TupleOffset = 0; cs_error(link, RequestIO, last_ret);
goto failed;
tuple.DesiredTuple = CISTPL_CFTABLE_ENTRY;
CS_CHECK(GetFirstTuple, pcmcia_get_first_tuple(link, &tuple));
while (1) {
if (pcmcia_get_tuple_data(link, &tuple) != 0 ||
pcmcia_parse_tuple(link, &tuple, &parse) != 0)
goto next_entry;
link->conf.ConfigIndex = parse.cftable_entry.index;
link->io.BasePort1 = parse.cftable_entry.io.win[0].base;
link->io.NumPorts1 = parse.cftable_entry.io.win[0].len;
if (link->io.BasePort1 != 0) {
i = pcmcia_request_io(link, &link->io);
if (i == CS_SUCCESS)
break;
}
next_entry:
CS_CHECK(GetNextTuple, pcmcia_get_next_tuple(link, &tuple));
} }
CS_CHECK(RequestIRQ, pcmcia_request_irq(link, &link->irq)); CS_CHECK(RequestIRQ, pcmcia_request_irq(link, &link->irq));
...@@ -831,6 +825,7 @@ err_release: ...@@ -831,6 +825,7 @@ err_release:
cs_failed: cs_failed:
cs_error(link, last_fn, last_ret); cs_error(link, last_fn, last_ret);
failed:
SYM53C500_release(link); SYM53C500_release(link);
return -ENODEV; return -ENODEV;
} /* SYM53C500_config */ } /* SYM53C500_config */
......
Markdown is supported
0%
or
You are about to add 0 people to the discussion. Proceed with caution.
Finish editing this message first!
Please register or to comment