Re: [PATCH] mpc512x: Reset module

2009-09-07 Thread Wolfram Sang
Hi,

On Mon, Sep 07, 2009 at 10:06:01AM +1000, Damien Dusha wrote:
 Dear all,
 
 I have written a small patch to get the software reset working on the
 mpc5121.  It is similar to the reset driver found in
 arch/powerpc/platforms/83xx/misc.c except it has been modified to look
 for the reset node in the device tree before writing to the reset
 module.

Heh, my patch looks quite similar :)

From: Wolfram Sang w.s...@pengutronix.de
Subject: mpc5121: add restart capability

Hack? Not intended for upstream yet.

Signed-off-by: Wolfram Sang w.s...@pengutronix.de
---
 arch/powerpc/platforms/512x/mpc5121_generic.c |   32 ++
 1 file changed, 32 insertions(+)

Index: arch/powerpc/platforms/512x/mpc5121_generic.c
===
--- arch/powerpc/platforms/512x/mpc5121_generic.c.orig
+++ arch/powerpc/platforms/512x/mpc5121_generic.c
@@ -20,6 +20,7 @@
 #include asm/ipic.h
 #include asm/prom.h
 #include asm/time.h
+#include asm/mpc512x.h
 
 #include mpc512x.h
 
@@ -49,6 +50,36 @@ static int __init mpc5121_generic_probe(
return board[i] != NULL;
 }
 
+static void mpc5121_restart(char *cmd) {
+
+   struct mpc512x_reset_module *rm;
+   struct device_node *rmnode;
+
+   /* HACK: Proably not good from IRQ context */
+
+   rmnode = of_find_compatible_node(NULL, NULL, fsl,mpc5121-reset);
+   if (!rmnode) {
+   printk(KERN_ERR Missing 'fsl,mpc5121-reset' 
+   node in device tree!\n);
+   goto out;
+   }
+
+   rm = of_iomap(rmnode, 0);
+   if (!rm) {
+   printk(KERN_ERR Error mapping reset module node!\n);
+   goto out;
+   }
+
+   local_irq_disable();
+
+   /* Unlock register first, then reset */
+   out_be32(rm-rpr, 0x52535445);
+   out_be32(rm-rcr, 0x0002);
+out:
+   while (1) ;
+}
+
 define_machine(mpc5121_generic) {
.name   = MPC5121 generic,
.probe  = mpc5121_generic_probe,
@@ -56,4 +89,5 @@ define_machine(mpc5121_generic) {
.init_IRQ   = mpc512x_init_IRQ,
.get_irq= ipic_get_irq,
.calibrate_decr = generic_calibrate_decr,
+   .restart= mpc5121_restart,
 };



There is one reason which I wanted to check before submitting this (alas, no
time :( ). From mpc52xx_common.c:

...
/*
 * This variable is mapped in mpc52xx_map_wdt() and used in mpc52xx_restart().
 * Permanent mapping is required because mpc52xx_restart() can be called
 * from interrupt context while node mapping (which calls ioremap())
 * cannot be used at such point.
 */
static DEFINE_SPINLOCK(mpc52xx_lock);
static struct mpc52xx_gpt __iomem *mpc52xx_wdt;
...

I think this may be needed here also...

 
 Comments are welcome.  It's my first patch to the mailing list, so
 I'll apologise in advance for any problems with the submission
 procedure.
 
 Damien.

 diff --git a/arch/powerpc/platforms/512x/mpc5121_ads.c 
 b/arch/powerpc/platforms/512x/mpc5121_ads.c
 index a8976b4..16ca250 100644
 --- a/arch/powerpc/platforms/512x/mpc5121_ads.c
 +++ b/arch/powerpc/platforms/512x/mpc5121_ads.c
 @@ -70,4 +70,5 @@ define_machine(mpc5121_ads) {
   .init_IRQ   = mpc5121_ads_init_IRQ,
   .get_irq= ipic_get_irq,
   .calibrate_decr = generic_calibrate_decr,
 +.restart= mpc512x_restart,

Please use tabs and not spaces (See CodingStyle).

  };
 diff --git a/arch/powerpc/platforms/512x/mpc512x.h 
 b/arch/powerpc/platforms/512x/mpc512x.h
 index f4db8a7..d77f0ab 100644
 --- a/arch/powerpc/platforms/512x/mpc512x.h
 +++ b/arch/powerpc/platforms/512x/mpc512x.h
 @@ -14,5 +14,6 @@
  extern unsigned long mpc512x_find_ips_freq(struct device_node *node);
  extern void __init mpc512x_init_IRQ(void);
  extern void __init mpc512x_init_i2c(void);
 +extern void mpc512x_restart(char *cmd);

Um, do we need that?

  void __init mpc512x_declare_of_platform_devices(void);
  #endif   /* __MPC512X_H__ */
 diff --git a/arch/powerpc/platforms/512x/mpc512x_shared.c 
 b/arch/powerpc/platforms/512x/mpc512x_shared.c
 index 135fd6b..deddafc 100644
 --- a/arch/powerpc/platforms/512x/mpc512x_shared.c
 +++ b/arch/powerpc/platforms/512x/mpc512x_shared.c
 @@ -22,6 +22,7 @@
  #include asm/prom.h
  #include asm/time.h
  
 +#include asm/mpc512x.h
  #include mpc512x.h
  
  unsigned long
 @@ -89,6 +90,33 @@ void __init mpc512x_init_i2c(void)
   }
  }
  
 +void mpc512x_restart(char *cmd)
 +{
 +struct device_node *np;

Again spaces instead of a tab.

 +struct mpc512x_reset_module *rm;
 +
 +local_irq_disable();
 +
 + np = of_find_compatible_node(NULL, NULL, fsl,mpc5121-reset);
 +
 + if (np) {
 +
 +rm = of_iomap(np, 0);
 + if (rm) {

Here you used tabs :)

 +
 +/* Enable software reset RSTE (in hex) */
 +out_be32( 

[PATCH] mpc512x: Reset module

2009-09-06 Thread Damien Dusha
Dear all,

I have written a small patch to get the software reset working on the
mpc5121.  It is similar to the reset driver found in
arch/powerpc/platforms/83xx/misc.c except it has been modified to look
for the reset node in the device tree before writing to the reset
module.

Comments are welcome.  It's my first patch to the mailing list, so
I'll apologise in advance for any problems with the submission
procedure.

Damien.
diff --git a/arch/powerpc/platforms/512x/mpc5121_ads.c b/arch/powerpc/platforms/512x/mpc5121_ads.c
index a8976b4..16ca250 100644
--- a/arch/powerpc/platforms/512x/mpc5121_ads.c
+++ b/arch/powerpc/platforms/512x/mpc5121_ads.c
@@ -70,4 +70,5 @@ define_machine(mpc5121_ads) {
 	.init_IRQ		= mpc5121_ads_init_IRQ,
 	.get_irq		= ipic_get_irq,
 	.calibrate_decr		= generic_calibrate_decr,
+.restart= mpc512x_restart,
 };
diff --git a/arch/powerpc/platforms/512x/mpc512x.h b/arch/powerpc/platforms/512x/mpc512x.h
index f4db8a7..d77f0ab 100644
--- a/arch/powerpc/platforms/512x/mpc512x.h
+++ b/arch/powerpc/platforms/512x/mpc512x.h
@@ -14,5 +14,6 @@
 extern unsigned long mpc512x_find_ips_freq(struct device_node *node);
 extern void __init mpc512x_init_IRQ(void);
 extern void __init mpc512x_init_i2c(void);
+extern void mpc512x_restart(char *cmd);
 void __init mpc512x_declare_of_platform_devices(void);
 #endif/* __MPC512X_H__ */
diff --git a/arch/powerpc/platforms/512x/mpc512x_shared.c b/arch/powerpc/platforms/512x/mpc512x_shared.c
index 135fd6b..deddafc 100644
--- a/arch/powerpc/platforms/512x/mpc512x_shared.c
+++ b/arch/powerpc/platforms/512x/mpc512x_shared.c
@@ -22,6 +22,7 @@
 #include asm/prom.h
 #include asm/time.h
 
+#include asm/mpc512x.h
 #include mpc512x.h
 
 unsigned long
@@ -89,6 +90,33 @@ void __init mpc512x_init_i2c(void)
 	}
 }
 
+void mpc512x_restart(char *cmd)
+{
+struct device_node *np;
+struct mpc512x_reset_module *rm;
+
+local_irq_disable();
+
+	np = of_find_compatible_node(NULL, NULL, fsl,mpc5121-reset);
+
+	if (np) {
+
+rm = of_iomap(np, 0);
+		if (rm) {
+
+/* Enable software reset RSTE (in hex) */
+out_be32( (rm-rpr) , 0x52535445);
+
+/* Set the software hard reset */
+out_be32( (rm-rcr), 0x2);
+}
+	}
+
+printk (KERN_EMERG Error: Unable to map reset module, spinning forever!\n);
+for(;;);
+}
+
+
 /*
  * Nodes to do bus probe on, soc and localbus
  */
___
Linuxppc-dev mailing list
Linuxppc-dev@lists.ozlabs.org
https://lists.ozlabs.org/listinfo/linuxppc-dev