aboutsummaryrefslogtreecommitdiffstats
path: root/arch/arm/mach-pxa/reset.c
diff options
context:
space:
mode:
authorDmitry Baryshkov <dbaryshkov@gmail.com>2008-05-22 11:20:18 -0400
committerRussell King <rmk+kernel@arm.linux.org.uk>2008-07-07 08:21:52 -0400
commit75f10b465af9efd59906e9079ed9cbda7e0f7a43 (patch)
tree84bb1a73c4856b0cc24d23075578f45a1b4e3eb3 /arch/arm/mach-pxa/reset.c
parentb8291ad07a7f3b5b990900f0001198ac23ba893e (diff)
[ARM] 5047/2: Support resetting by asserting GPIO pin
This adds support for resetting via assertion of GPIO pin. This e.g. is used on Sharp Zaurus SL-6000. Signed-off-by: Dmitry Baryshkov <dbaryshkov@gmail.com> Acked-by: Eric Miao <eric.miao@marvell.com> Signed-off-by: Russell King <rmk+kernel@arm.linux.org.uk>
Diffstat (limited to 'arch/arm/mach-pxa/reset.c')
-rw-r--r--arch/arm/mach-pxa/reset.c95
1 files changed, 95 insertions, 0 deletions
diff --git a/arch/arm/mach-pxa/reset.c b/arch/arm/mach-pxa/reset.c
new file mode 100644
index 000000000000..551f313c94df
--- /dev/null
+++ b/arch/arm/mach-pxa/reset.c
@@ -0,0 +1,95 @@
1/*
2 * This program is free software; you can redistribute it and/or modify
3 * it under the terms of the GNU General Public License version 2 as
4 * published by the Free Software Foundation.
5 */
6#include <linux/kernel.h>
7#include <linux/module.h>
8#include <linux/delay.h>
9#include <linux/gpio.h>
10#include <asm/io.h>
11#include <asm/proc-fns.h>
12
13#include <asm/arch/pxa-regs.h>
14
15static void do_hw_reset(void);
16
17static int reset_gpio = -1;
18
19int init_gpio_reset(int gpio)
20{
21 int rc;
22
23 rc = gpio_request(gpio, "reset generator");
24 if (rc) {
25 printk(KERN_ERR "Can't request reset_gpio\n");
26 goto out;
27 }
28
29 rc = gpio_direction_input(gpio);
30 if (rc) {
31 printk(KERN_ERR "Can't configure reset_gpio for input\n");
32 gpio_free(gpio);
33 goto out;
34 }
35
36out:
37 if (!rc)
38 reset_gpio = gpio;
39
40 return rc;
41}
42
43/*
44 * Trigger GPIO reset.
45 * This covers various types of logic connecting gpio pin
46 * to RESET pins (nRESET or GPIO_RESET):
47 */
48static void do_gpio_reset(void)
49{
50 BUG_ON(reset_gpio == -1);
51
52 /* drive it low */
53 gpio_direction_output(reset_gpio, 0);
54 mdelay(2);
55 /* rising edge or drive high */
56 gpio_set_value(reset_gpio, 1);
57 mdelay(2);
58 /* falling edge */
59 gpio_set_value(reset_gpio, 0);
60
61 /* give it some time */
62 mdelay(10);
63
64 WARN_ON(1);
65 /* fallback */
66 do_hw_reset();
67}
68
69static void do_hw_reset(void)
70{
71 /* Initialize the watchdog and let it fire */
72 OWER = OWER_WME;
73 OSSR = OSSR_M3;
74 OSMR3 = OSCR + 368640; /* ... in 100 ms */
75}
76
77void arch_reset(char mode)
78{
79 if (cpu_is_pxa2xx())
80 RCSR = RCSR_HWR | RCSR_WDR | RCSR_SMR | RCSR_GPR;
81
82 switch (mode) {
83 case 's':
84 /* Jump into ROM at address 0 */
85 cpu_reset(0);
86 break;
87 case 'h':
88 do_hw_reset();
89 break;
90 case 'g':
91 do_gpio_reset();
92 break;
93 }
94}
95