aboutsummaryrefslogtreecommitdiffstats
path: root/drivers
diff options
context:
space:
mode:
authorDavid Brownell <dbrownell@users.sourceforge.net>2008-02-05 01:27:42 -0500
committerLinus Torvalds <torvalds@woody.linux-foundation.org>2008-02-05 12:44:09 -0500
commit4c1fc445c29c6208c44e10c0253beea890bf5435 (patch)
tree2c52339b73cd6cf300b53f156d63f8ba0a7a4c94 /drivers
parent9ab9898e32971b938f9e8a997b12d0c4dd4832f7 (diff)
at91_cf: use generic gpio calls
Update the AT91 CF driver to use the generic GPIO calls instead of the AT91-specific ones; and request exclusive use of those signals. Minor tweaks to cleanup code paths: always in reverse order of how the resources were allocated, with remove() matching the fault paths of probe(). Signed-off-by: David Brownell <dbrownell@users.sourceforge.net> Signed-off-by: Andrew Morton <akpm@linux-foundation.org> Signed-off-by: Linus Torvalds <torvalds@linux-foundation.org>
Diffstat (limited to 'drivers')
-rw-r--r--drivers/pcmcia/at91_cf.c62
1 files changed, 47 insertions, 15 deletions
diff --git a/drivers/pcmcia/at91_cf.c b/drivers/pcmcia/at91_cf.c
index eb6abd3f9221..385e145e1acc 100644
--- a/drivers/pcmcia/at91_cf.c
+++ b/drivers/pcmcia/at91_cf.c
@@ -21,9 +21,9 @@
21#include <asm/hardware.h> 21#include <asm/hardware.h>
22#include <asm/io.h> 22#include <asm/io.h>
23#include <asm/sizes.h> 23#include <asm/sizes.h>
24#include <asm/gpio.h>
24 25
25#include <asm/arch/board.h> 26#include <asm/arch/board.h>
26#include <asm/arch/gpio.h>
27#include <asm/arch/at91rm9200_mc.h> 27#include <asm/arch/at91rm9200_mc.h>
28 28
29 29
@@ -56,7 +56,7 @@ struct at91_cf_socket {
56 56
57static inline int at91_cf_present(struct at91_cf_socket *cf) 57static inline int at91_cf_present(struct at91_cf_socket *cf)
58{ 58{
59 return !at91_get_gpio_value(cf->board->det_pin); 59 return !gpio_get_value(cf->board->det_pin);
60} 60}
61 61
62/*--------------------------------------------------------------------------*/ 62/*--------------------------------------------------------------------------*/
@@ -100,9 +100,9 @@ static int at91_cf_get_status(struct pcmcia_socket *s, u_int *sp)
100 int vcc = cf->board->vcc_pin; 100 int vcc = cf->board->vcc_pin;
101 101
102 *sp = SS_DETECT | SS_3VCARD; 102 *sp = SS_DETECT | SS_3VCARD;
103 if (!rdy || at91_get_gpio_value(rdy)) 103 if (!rdy || gpio_get_value(rdy))
104 *sp |= SS_READY; 104 *sp |= SS_READY;
105 if (!vcc || at91_get_gpio_value(vcc)) 105 if (!vcc || gpio_get_value(vcc))
106 *sp |= SS_POWERON; 106 *sp |= SS_POWERON;
107 } else 107 } else
108 *sp = 0; 108 *sp = 0;
@@ -121,10 +121,10 @@ at91_cf_set_socket(struct pcmcia_socket *sock, struct socket_state_t *s)
121 if (cf->board->vcc_pin) { 121 if (cf->board->vcc_pin) {
122 switch (s->Vcc) { 122 switch (s->Vcc) {
123 case 0: 123 case 0:
124 at91_set_gpio_value(cf->board->vcc_pin, 0); 124 gpio_set_value(cf->board->vcc_pin, 0);
125 break; 125 break;
126 case 33: 126 case 33:
127 at91_set_gpio_value(cf->board->vcc_pin, 1); 127 gpio_set_value(cf->board->vcc_pin, 1);
128 break; 128 break;
129 default: 129 default:
130 return -EINVAL; 130 return -EINVAL;
@@ -132,7 +132,7 @@ at91_cf_set_socket(struct pcmcia_socket *sock, struct socket_state_t *s)
132 } 132 }
133 133
134 /* toggle reset if needed */ 134 /* toggle reset if needed */
135 at91_set_gpio_value(cf->board->rst_pin, s->flags & SS_RESET); 135 gpio_set_value(cf->board->rst_pin, s->flags & SS_RESET);
136 136
137 pr_debug("%s: Vcc %d, io_irq %d, flags %04x csc %04x\n", 137 pr_debug("%s: Vcc %d, io_irq %d, flags %04x csc %04x\n",
138 driver_name, s->Vcc, s->io_irq, s->flags, s->csc_mask); 138 driver_name, s->Vcc, s->io_irq, s->flags, s->csc_mask);
@@ -239,11 +239,24 @@ static int __init at91_cf_probe(struct platform_device *pdev)
239 platform_set_drvdata(pdev, cf); 239 platform_set_drvdata(pdev, cf);
240 240
241 /* must be a GPIO; ergo must trigger on both edges */ 241 /* must be a GPIO; ergo must trigger on both edges */
242 status = request_irq(board->det_pin, at91_cf_irq, 0, driver_name, cf); 242 status = gpio_request(board->det_pin, "cf_det");
243 if (status < 0) 243 if (status < 0)
244 goto fail0; 244 goto fail0;
245 status = request_irq(board->det_pin, at91_cf_irq, 0, driver_name, cf);
246 if (status < 0)
247 goto fail00;
245 device_init_wakeup(&pdev->dev, 1); 248 device_init_wakeup(&pdev->dev, 1);
246 249
250 status = gpio_request(board->rst_pin, "cf_rst");
251 if (status < 0)
252 goto fail0a;
253
254 if (board->vcc_pin) {
255 status = gpio_request(board->vcc_pin, "cf_vcc");
256 if (status < 0)
257 goto fail0b;
258 }
259
247 /* 260 /*
248 * The card driver will request this irq later as needed. 261 * The card driver will request this irq later as needed.
249 * but it causes lots of "irqNN: nobody cared" messages 262 * but it causes lots of "irqNN: nobody cared" messages
@@ -251,16 +264,20 @@ static int __init at91_cf_probe(struct platform_device *pdev)
251 * (Note: DK board doesn't wire the IRQ pin...) 264 * (Note: DK board doesn't wire the IRQ pin...)
252 */ 265 */
253 if (board->irq_pin) { 266 if (board->irq_pin) {
267 status = gpio_request(board->irq_pin, "cf_irq");
268 if (status < 0)
269 goto fail0c;
254 status = request_irq(board->irq_pin, at91_cf_irq, 270 status = request_irq(board->irq_pin, at91_cf_irq,
255 IRQF_SHARED, driver_name, cf); 271 IRQF_SHARED, driver_name, cf);
256 if (status < 0) 272 if (status < 0)
257 goto fail0a; 273 goto fail0d;
258 cf->socket.pci_irq = board->irq_pin; 274 cf->socket.pci_irq = board->irq_pin;
259 } else 275 } else
260 cf->socket.pci_irq = NR_IRQS + 1; 276 cf->socket.pci_irq = NR_IRQS + 1;
261 277
262 /* pcmcia layer only remaps "real" memory not iospace */ 278 /* pcmcia layer only remaps "real" memory not iospace */
263 cf->socket.io_offset = (unsigned long) ioremap(cf->phys_baseaddr + CF_IO_PHYS, SZ_2K); 279 cf->socket.io_offset = (unsigned long)
280 ioremap(cf->phys_baseaddr + CF_IO_PHYS, SZ_2K);
264 if (!cf->socket.io_offset) { 281 if (!cf->socket.io_offset) {
265 status = -ENXIO; 282 status = -ENXIO;
266 goto fail1; 283 goto fail1;
@@ -296,11 +313,21 @@ fail2:
296fail1: 313fail1:
297 if (cf->socket.io_offset) 314 if (cf->socket.io_offset)
298 iounmap((void __iomem *) cf->socket.io_offset); 315 iounmap((void __iomem *) cf->socket.io_offset);
299 if (board->irq_pin) 316 if (board->irq_pin) {
300 free_irq(board->irq_pin, cf); 317 free_irq(board->irq_pin, cf);
318fail0d:
319 gpio_free(board->irq_pin);
320 }
321fail0c:
322 if (board->vcc_pin)
323 gpio_free(board->vcc_pin);
324fail0b:
325 gpio_free(board->rst_pin);
301fail0a: 326fail0a:
302 device_init_wakeup(&pdev->dev, 0); 327 device_init_wakeup(&pdev->dev, 0);
303 free_irq(board->det_pin, cf); 328 free_irq(board->det_pin, cf);
329fail00:
330 gpio_free(board->det_pin);
304fail0: 331fail0:
305 kfree(cf); 332 kfree(cf);
306 return status; 333 return status;
@@ -313,13 +340,18 @@ static int __exit at91_cf_remove(struct platform_device *pdev)
313 struct resource *io = cf->socket.io[0].res; 340 struct resource *io = cf->socket.io[0].res;
314 341
315 pcmcia_unregister_socket(&cf->socket); 342 pcmcia_unregister_socket(&cf->socket);
316 if (board->irq_pin) 343 release_mem_region(io->start, io->end + 1 - io->start);
344 iounmap((void __iomem *) cf->socket.io_offset);
345 if (board->irq_pin) {
317 free_irq(board->irq_pin, cf); 346 free_irq(board->irq_pin, cf);
347 gpio_free(board->irq_pin);
348 }
349 if (board->vcc_pin)
350 gpio_free(board->vcc_pin);
351 gpio_free(board->rst_pin);
318 device_init_wakeup(&pdev->dev, 0); 352 device_init_wakeup(&pdev->dev, 0);
319 free_irq(board->det_pin, cf); 353 free_irq(board->det_pin, cf);
320 iounmap((void __iomem *) cf->socket.io_offset); 354 gpio_free(board->det_pin);
321 release_mem_region(io->start, io->end + 1 - io->start);
322
323 kfree(cf); 355 kfree(cf);
324 return 0; 356 return 0;
325} 357}