Blackfin: handle new anomalies with reset
authorMike Frysinger <vapier@gentoo.org>
Sun, 12 Oct 2008 01:49:06 +0000 (21:49 -0400)
committerMike Frysinger <vapier@gentoo.org>
Wed, 28 Jan 2009 18:26:15 +0000 (13:26 -0500)
Workaround fun new anomalies related to software reset of the processor.

Signed-off-by: Mike Frysinger <vapier@gentoo.org>
cpu/blackfin/reset.c

index d1e34b3f94ce9d849c4300c02295cbb99bcc8164..284cea579d0bad4a035b3c24c7c900a32557e544 100644 (file)
@@ -29,26 +29,35 @@ void bfin_reset(void)
         */
        __builtin_bfin_ssync();
 
-       while (1) {
+       /* The bootrom checks to see how it was reset and will
+        * automatically perform a software reset for us when
+        * it starts executing after the core reset.
+        */
+       if (ANOMALY_05000353 || ANOMALY_05000386) {
                /* Initiate System software reset. */
                bfin_write_SWRST(0x7);
 
                /* Due to the way reset is handled in the hardware, we need
-                * to delay for 7 SCLKS.  The only reliable way to do this is
-                * to calculate the CCLK/SCLK ratio and multiply 7.  For now,
+                * to delay for 10 SCLKS.  The only reliable way to do this is
+                * to calculate the CCLK/SCLK ratio and multiply 10.  For now,
                 * we'll assume worse case which is a 1:15 ratio.
                 */
                asm(
                        "LSETUP (1f, 1f) LC0 = %0\n"
                        "1: nop;"
                        :
-                       : "a" (15 * 7)
+                       : "a" (15 * 10)
                        : "LC0", "LB0", "LT0"
                );
 
                /* Clear System software reset */
                bfin_write_SWRST(0);
 
+               /* The BF526 ROM will crash during reset */
+#if defined(__ADSPBF522__) || defined(__ADSPBF524__) || defined(__ADSPBF526__)
+               bfin_read_SWRST();
+#endif
+
                /* Wait for the SWRST write to complete.  Cannot rely on SSYNC
                 * though as the System state is all reset now.
                 */
@@ -59,10 +68,11 @@ void bfin_reset(void)
                        : "a" (15 * 1)
                        : "LC1", "LB1", "LT1"
                );
+       }
 
+       while (1)
                /* Issue core reset */
                asm("raise 1");
-       }
 }
 
 /* We need to trampoline ourselves up into L1 since our linker