aboutsummaryrefslogtreecommitdiffstats
path: root/drivers/pcmcia/sa1100_h3600.c
diff options
context:
space:
mode:
Diffstat (limited to 'drivers/pcmcia/sa1100_h3600.c')
-rw-r--r--drivers/pcmcia/sa1100_h3600.c82
1 files changed, 71 insertions, 11 deletions
diff --git a/drivers/pcmcia/sa1100_h3600.c b/drivers/pcmcia/sa1100_h3600.c
index 3a121ac697d6..97e5667fb2e3 100644
--- a/drivers/pcmcia/sa1100_h3600.c
+++ b/drivers/pcmcia/sa1100_h3600.c
@@ -10,26 +10,78 @@
10#include <linux/interrupt.h> 10#include <linux/interrupt.h>
11#include <linux/init.h> 11#include <linux/init.h>
12#include <linux/delay.h> 12#include <linux/delay.h>
13#include <linux/gpio.h>
13 14
14#include <mach/hardware.h> 15#include <mach/hardware.h>
15#include <asm/irq.h> 16#include <asm/irq.h>
16#include <asm/mach-types.h> 17#include <asm/mach-types.h>
17#include <mach/h3600.h> 18#include <mach/h3600.h>
19#include <mach/h3600_gpio.h>
18 20
19#include "sa1100_generic.h" 21#include "sa1100_generic.h"
20 22
21static struct pcmcia_irqs irqs[] = { 23static struct pcmcia_irqs irqs[] = {
22 { 0, IRQ_GPIO_H3600_PCMCIA_CD0, "PCMCIA CD0" }, 24 { .sock = 0, .str = "PCMCIA CD0" }, /* .irq will be filled later */
23 { 1, IRQ_GPIO_H3600_PCMCIA_CD1, "PCMCIA CD1" } 25 { .sock = 1, .str = "PCMCIA CD1" }
24}; 26};
25 27
26static int h3600_pcmcia_hw_init(struct soc_pcmcia_socket *skt) 28static int h3600_pcmcia_hw_init(struct soc_pcmcia_socket *skt)
27{ 29{
28 skt->socket.pci_irq = skt->nr ? IRQ_GPIO_H3600_PCMCIA_IRQ1 30 int err;
29 : IRQ_GPIO_H3600_PCMCIA_IRQ0;
30 31
32 switch (skt->nr) {
33 case 0:
34 err = gpio_request(H3XXX_GPIO_PCMCIA_IRQ0, "PCMCIA IRQ0");
35 if (err)
36 goto err00;
37 err = gpio_direction_input(H3XXX_GPIO_PCMCIA_IRQ0);
38 if (err)
39 goto err01;
40 skt->socket.pci_irq = gpio_to_irq(H3XXX_GPIO_PCMCIA_IRQ0);
41
42 err = gpio_request(H3XXX_GPIO_PCMCIA_CD0, "PCMCIA CD0");
43 if (err)
44 goto err01;
45 err = gpio_direction_input(H3XXX_GPIO_PCMCIA_CD0);
46 if (err)
47 goto err02;
48 irqs[0].irq = gpio_to_irq(H3XXX_GPIO_PCMCIA_CD0);
49
50 err = soc_pcmcia_request_irqs(skt, irqs, ARRAY_SIZE(irqs));
51 if (err)
52 goto err02;
53 break;
54 case 1:
55 err = gpio_request(H3XXX_GPIO_PCMCIA_IRQ1, "PCMCIA IRQ1");
56 if (err)
57 goto err10;
58 err = gpio_direction_input(H3XXX_GPIO_PCMCIA_IRQ1);
59 if (err)
60 goto err11;
61 skt->socket.pci_irq = gpio_to_irq(H3XXX_GPIO_PCMCIA_IRQ1);
62
63 err = gpio_request(H3XXX_GPIO_PCMCIA_CD1, "PCMCIA CD1");
64 if (err)
65 goto err11;
66 err = gpio_direction_input(H3XXX_GPIO_PCMCIA_CD1);
67 if (err)
68 goto err12;
69 irqs[1].irq = gpio_to_irq(H3XXX_GPIO_PCMCIA_CD1);
70
71 err = soc_pcmcia_request_irqs(skt, irqs, ARRAY_SIZE(irqs));
72 if (err)
73 goto err12;
74 break;
75 }
76 return 0;
77
78err02: gpio_free(H3XXX_GPIO_PCMCIA_CD0);
79err01: gpio_free(H3XXX_GPIO_PCMCIA_IRQ0);
80err00: return err;
31 81
32 return soc_pcmcia_request_irqs(skt, irqs, ARRAY_SIZE(irqs)); 82err12: gpio_free(H3XXX_GPIO_PCMCIA_CD0);
83err11: gpio_free(H3XXX_GPIO_PCMCIA_IRQ0);
84err10: return err;
33} 85}
34 86
35static void h3600_pcmcia_hw_shutdown(struct soc_pcmcia_socket *skt) 87static void h3600_pcmcia_hw_shutdown(struct soc_pcmcia_socket *skt)
@@ -40,17 +92,25 @@ static void h3600_pcmcia_hw_shutdown(struct soc_pcmcia_socket *skt)
40 assign_h3600_egpio(IPAQ_EGPIO_OPT_NVRAM_ON, 0); 92 assign_h3600_egpio(IPAQ_EGPIO_OPT_NVRAM_ON, 0);
41 assign_h3600_egpio(IPAQ_EGPIO_OPT_ON, 0); 93 assign_h3600_egpio(IPAQ_EGPIO_OPT_ON, 0);
42 assign_h3600_egpio(IPAQ_EGPIO_OPT_RESET, 1); 94 assign_h3600_egpio(IPAQ_EGPIO_OPT_RESET, 1);
95 switch (skt->nr) {
96 case 0:
97 gpio_free(H3XXX_GPIO_PCMCIA_CD0);
98 gpio_free(H3XXX_GPIO_PCMCIA_IRQ0);
99 break;
100 case 1:
101 gpio_free(H3XXX_GPIO_PCMCIA_CD1);
102 gpio_free(H3XXX_GPIO_PCMCIA_IRQ1);
103 break;
104 }
43} 105}
44 106
45static void 107static void
46h3600_pcmcia_socket_state(struct soc_pcmcia_socket *skt, struct pcmcia_state *state) 108h3600_pcmcia_socket_state(struct soc_pcmcia_socket *skt, struct pcmcia_state *state)
47{ 109{
48 unsigned long levels = GPLR;
49
50 switch (skt->nr) { 110 switch (skt->nr) {
51 case 0: 111 case 0:
52 state->detect = levels & GPIO_H3600_PCMCIA_CD0 ? 0 : 1; 112 state->detect = !gpio_get_value(H3XXX_GPIO_PCMCIA_CD0);
53 state->ready = levels & GPIO_H3600_PCMCIA_IRQ0 ? 1 : 0; 113 state->ready = !!gpio_get_value(H3XXX_GPIO_PCMCIA_IRQ0);
54 state->bvd1 = 0; 114 state->bvd1 = 0;
55 state->bvd2 = 0; 115 state->bvd2 = 0;
56 state->wrprot = 0; /* Not available on H3600. */ 116 state->wrprot = 0; /* Not available on H3600. */
@@ -59,8 +119,8 @@ h3600_pcmcia_socket_state(struct soc_pcmcia_socket *skt, struct pcmcia_state *st
59 break; 119 break;
60 120
61 case 1: 121 case 1:
62 state->detect = levels & GPIO_H3600_PCMCIA_CD1 ? 0 : 1; 122 state->detect = !gpio_get_value(H3XXX_GPIO_PCMCIA_CD1);
63 state->ready = levels & GPIO_H3600_PCMCIA_IRQ1 ? 1 : 0; 123 state->ready = !!gpio_get_value(H3XXX_GPIO_PCMCIA_IRQ1);
64 state->bvd1 = 0; 124 state->bvd1 = 0;
65 state->bvd2 = 0; 125 state->bvd2 = 0;
66 state->wrprot = 0; /* Not available on H3600. */ 126 state->wrprot = 0; /* Not available on H3600. */