summaryrefslogtreecommitdiffstats
path: root/sys/powerpc
diff options
context:
space:
mode:
authornwhitehorn <nwhitehorn@FreeBSD.org>2015-01-21 02:57:54 +0000
committernwhitehorn <nwhitehorn@FreeBSD.org>2015-01-21 02:57:54 +0000
commit301885260edcb68943c33844bd5d522ef7caaf2f (patch)
treef4ed4c8d193c1aa8884acca96bb1f8488bb30979 /sys/powerpc
parentb4fa4f6baa40f0815a0bad3475903e47fee4b076 (diff)
downloadFreeBSD-src-301885260edcb68943c33844bd5d522ef7caaf2f.zip
FreeBSD-src-301885260edcb68943c33844bd5d522ef7caaf2f.tar.gz
On 64-bit PowerPC, use more native forms of the PPC 970 HID restore
sequences, like are used to read the HIDs. This is both easier to read and avoids a miscompilation by GCC in certain circumstances. Also avoid double restoration of HID4 and HID5. MFC after: 2 weeks
Diffstat (limited to 'sys/powerpc')
-rw-r--r--sys/powerpc/aim/mp_cpudep.c29
1 files changed, 23 insertions, 6 deletions
diff --git a/sys/powerpc/aim/mp_cpudep.c b/sys/powerpc/aim/mp_cpudep.c
index 3bc21a4..59a24e2 100644
--- a/sys/powerpc/aim/mp_cpudep.c
+++ b/sys/powerpc/aim/mp_cpudep.c
@@ -58,7 +58,9 @@ SYSINIT(cpu_save_config, SI_SUB_CPU, SI_ORDER_ANY, cpudep_save_config, NULL);
void
cpudep_ap_early_bootstrap(void)
{
+#ifndef __powerpc64__
register_t reg;
+#endif
__asm __volatile("mtsprg 0, %0" :: "r"(ap_pcpu));
powerpc_sync();
@@ -69,12 +71,17 @@ cpudep_ap_early_bootstrap(void)
case IBM970MP:
/* Restore HID4 and HID5, which are necessary for the MMU */
+#ifdef __powerpc64__
+ mtspr(SPR_HID4, bsp_state[2]); powerpc_sync(); isync();
+ mtspr(SPR_HID5, bsp_state[3]); powerpc_sync(); isync();
+#else
__asm __volatile("ld %0, 16(%2); sync; isync; \
mtspr %1, %0; sync; isync;"
: "=r"(reg) : "K"(SPR_HID4), "r"(bsp_state));
__asm __volatile("ld %0, 24(%2); sync; isync; \
mtspr %1, %0; sync; isync;"
: "=r"(reg) : "K"(SPR_HID5), "r"(bsp_state));
+#endif
powerpc_sync();
break;
}
@@ -292,9 +299,24 @@ cpudep_ap_setup()
/*
* The 970 has strange rules about how to update HID registers.
* See Table 2-3, 970MP manual
+ *
+ * Note: HID4 and HID5 restored already in
+ * cpudep_ap_early_bootstrap()
*/
__asm __volatile("mtasr %0; sync" :: "r"(0));
+ #ifdef __powerpc64__
+ __asm __volatile(" \
+ sync; isync; \
+ mtspr %1, %0; \
+ mfspr %0, %1; mfspr %0, %1; mfspr %0, %1; \
+ mfspr %0, %1; mfspr %0, %1; mfspr %0, %1; \
+ sync; isync"
+ :: "r"(bsp_state[0]), "K"(SPR_HID0));
+ __asm __volatile("sync; isync; \
+ mtspr %1, %0; mtspr %1, %0; sync; isync"
+ :: "r"(bsp_state[1]), "K"(SPR_HID1));
+ #else
__asm __volatile(" \
ld %0,0(%2); \
sync; isync; \
@@ -306,12 +328,7 @@ cpudep_ap_setup()
__asm __volatile("ld %0, 8(%2); sync; isync; \
mtspr %1, %0; mtspr %1, %0; sync; isync"
: "=r"(reg) : "K"(SPR_HID1), "r"(bsp_state));
- __asm __volatile("ld %0, 16(%2); sync; isync; \
- mtspr %1, %0; sync; isync;"
- : "=r"(reg) : "K"(SPR_HID4), "r"(bsp_state));
- __asm __volatile("ld %0, 24(%2); sync; isync; \
- mtspr %1, %0; sync; isync;"
- : "=r"(reg) : "K"(SPR_HID5), "r"(bsp_state));
+ #endif
powerpc_sync();
break;
OpenPOWER on IntegriCloud