diff options
Diffstat (limited to 'drivers/pcmcia/sa1100_h3600.c')
-rw-r--r-- | drivers/pcmcia/sa1100_h3600.c | 97 |
1 files changed, 35 insertions, 62 deletions
diff --git a/drivers/pcmcia/sa1100_h3600.c b/drivers/pcmcia/sa1100_h3600.c index a6d387d9ec4d..2e9265e59ae4 100644 --- a/drivers/pcmcia/sa1100_h3600.c +++ b/drivers/pcmcia/sa1100_h3600.c @@ -5,23 +5,23 @@ * PCMCIA implementation routines for H3600 * */ -#include <linux/module.h> #include <linux/kernel.h> #include <linux/device.h> -#include <linux/interrupt.h> -#include <linux/init.h> -#include <linux/delay.h> -#include <linux/gpio.h> -#include <mach/hardware.h> -#include <asm/irq.h> #include <asm/mach-types.h> -#include <mach/h3xxx.h> +#include "l1110.h" #include "sa1100_generic.h" -static int h3600_pcmcia_hw_init(struct soc_pcmcia_socket *skt) +struct ipaq_option_id { + u16 vendor; + u16 device; +}; + +static int l1110_pcmcia_hw_init(struct soc_pcmcia_socket *skt) { + struct device *dev = skt->socket.dev.parent; + struct l1110 *l; int err; skt->stat[SOC_STAT_CD].name = skt->nr ? "pcmcia1-detect" : "pcmcia0-detect"; @@ -31,75 +31,48 @@ static int h3600_pcmcia_hw_init(struct soc_pcmcia_socket *skt) if (err) return err; - switch (skt->nr) { - case 0: - err = gpio_request(H3XXX_EGPIO_CARD_RESET, "PCMCIA CARD RESET"); - if (err) - goto err05; - err = gpio_direction_output(H3XXX_EGPIO_CARD_RESET, 0); - if (err) - goto err06; - break; - case 1: - break; - } - return 0; + err = l1110_init(dev, &l, skt->nr ? 0x19000000 : 0x1a000000, + skt->nr); + if (err) + return err; -err06: gpio_free(H3XXX_EGPIO_CARD_RESET); -err05: return err; -} + skt->socket.driver_data = l; -static void h3600_pcmcia_hw_shutdown(struct soc_pcmcia_socket *skt) -{ - switch (skt->nr) { - case 0: - /* Disable CF bus: */ - gpio_free(H3XXX_EGPIO_CARD_RESET); - break; - case 1: - break; - } + return 0; } -static void -h3600_pcmcia_socket_state(struct soc_pcmcia_socket *skt, struct pcmcia_state *state) +static void l1110_pcmcia_socket_state(struct soc_pcmcia_socket *skt, + struct pcmcia_state *state) { - state->bvd1 = 0; - state->bvd2 = 0; - state->vs_3v = 0; - state->vs_Xv = 0; + struct l1110 *l = skt->socket.driver_data; + + l1110_socket_state(l, state); } -static int -h3600_pcmcia_configure_socket(struct soc_pcmcia_socket *skt, const socket_state_t *state) +static int l1110_pcmcia_configure_socket(struct soc_pcmcia_socket *skt, + const socket_state_t *state) { - if (state->Vcc != 0 && state->Vcc != 33 && state->Vcc != 50) { - printk(KERN_ERR "h3600_pcmcia: unrecognized Vcc %u.%uV\n", - state->Vcc / 10, state->Vcc % 10); - return -1; - } - - gpio_set_value(H3XXX_EGPIO_CARD_RESET, !!(state->flags & SS_RESET)); + struct l1110 *l = skt->socket.driver_data; - /* Silently ignore Vpp, output enable, speaker enable. */ - - return 0; + return l1110_configure_socket(l, state); } -struct pcmcia_low_level h3600_pcmcia_ops = { +static struct pcmcia_low_level l1110_pcmcia_ops = { .owner = THIS_MODULE, - .hw_init = h3600_pcmcia_hw_init, - .hw_shutdown = h3600_pcmcia_hw_shutdown, - .socket_state = h3600_pcmcia_socket_state, - .configure_socket = h3600_pcmcia_configure_socket, + .hw_init = l1110_pcmcia_hw_init, + .socket_state = l1110_pcmcia_socket_state, + .configure_socket = l1110_pcmcia_configure_socket, }; int pcmcia_h3600_init(struct device *dev) { - int ret = -ENODEV; + struct ipaq_option_id *id = dev->platform_data; + + if ((!machine_is_h3600() && !machine_is_h3100()) || !id) + return -ENODEV; - if (machine_is_h3600() || machine_is_h3100()) - ret = sa11xx_drv_pcmcia_probe(dev, &h3600_pcmcia_ops, 0, 2); + if (id->vendor != 0x1125 || id->device != 0x0001) + return -ENODEV; - return ret; + return sa11xx_drv_pcmcia_probe(dev, &l1110_pcmcia_ops, 0, 2); } |