Source-Changes-HG archive
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index][Old Index]
[src/trunk]: src/sys/arch/powerpc Move powerpc to use pcu to manage FPU/AltiV...
details: https://anonhg.NetBSD.org/src/rev/2191d0d74c97
branches: trunk
changeset: 764724:2191d0d74c97
user: matt <matt%NetBSD.org@localhost>
date: Mon May 02 02:01:32 2011 +0000
description:
Move powerpc to use pcu to manage FPU/AltiVec/SPE.
diffstat:
sys/arch/powerpc/booke/spe.c | 142 ++++-------
sys/arch/powerpc/booke/trap.c | 6 +-
sys/arch/powerpc/conf/files.powerpc | 4 +-
sys/arch/powerpc/include/altivec.h | 34 ++-
sys/arch/powerpc/include/fpu.h | 43 ++-
sys/arch/powerpc/include/proc.h | 12 +-
sys/arch/powerpc/include/psl.h | 6 +-
sys/arch/powerpc/include/types.h | 8 +-
sys/arch/powerpc/include/userret.h | 53 +----
sys/arch/powerpc/oea/altivec.c | 233 ++++++-------------
sys/arch/powerpc/pic/ipi.c | 12 +-
sys/arch/powerpc/powerpc/compat_16_machdep.c | 9 +-
sys/arch/powerpc/powerpc/core_machdep.c | 14 +-
sys/arch/powerpc/powerpc/fpu.c | 315 ++++++++++----------------
sys/arch/powerpc/powerpc/powerpc_machdep.c | 25 +-
sys/arch/powerpc/powerpc/process_machdep.c | 51 ++-
sys/arch/powerpc/powerpc/trap.c | 23 +-
sys/arch/powerpc/powerpc/vm_machdep.c | 13 +-
18 files changed, 426 insertions(+), 577 deletions(-)
diffs (truncated from 1693 to 300 lines):
diff -r cf0c3267cdc8 -r 2191d0d74c97 sys/arch/powerpc/booke/spe.c
--- a/sys/arch/powerpc/booke/spe.c Mon May 02 01:49:23 2011 +0000
+++ b/sys/arch/powerpc/booke/spe.c Mon May 02 02:01:32 2011 +0000
@@ -1,4 +1,4 @@
-/* $NetBSD: spe.c,v 1.2 2011/01/18 01:02:52 matt Exp $ */
+/* $NetBSD: spe.c,v 1.3 2011/05/02 02:01:32 matt Exp $ */
/*-
* Copyright (c) 2011 The NetBSD Foundation, Inc.
@@ -30,7 +30,7 @@
*/
#include <sys/cdefs.h>
-__KERNEL_RCSID(0, "$NetBSD: spe.c,v 1.2 2011/01/18 01:02:52 matt Exp $");
+__KERNEL_RCSID(0, "$NetBSD: spe.c,v 1.3 2011/05/02 02:01:32 matt Exp $");
#include "opt_altivec.h"
@@ -41,6 +41,7 @@
#include <sys/systm.h>
#include <sys/atomic.h>
#include <sys/siginfo.h>
+#include <sys/pcu.h>
#include <powerpc/altivec.h>
#include <powerpc/spr.h>
@@ -48,13 +49,33 @@
#include <powerpc/psl.h>
#include <powerpc/pcb.h>
-void
-vec_enable(void)
+static void vec_state_load(lwp_t *, bool);
+static void vec_state_save(lwp_t *);
+static void vec_state_release(lwp_t *);
+
+const pcu_ops_t vec_ops = {
+ .pcu_id = PCU_VEC,
+ .pcu_state_load = vec_state_load,
+ .pcu_state_save = vec_state_save,
+ .pcu_state_release = vec_state_release,
+};
+
+bool
+vec_used_p(lwp_t *l)
{
- struct cpu_info * const ci = curcpu();
- lwp_t * const l = curlwp;
+ return (l->l_md.md_flags & MDLWP_USEDVEC) != 0;
+}
+void
+vec_mark_used(lwp_t *l)
+{
l->l_md.md_flags |= MDLWP_USEDVEC;
+}
+
+void
+vec_state_load(lwp_t *l, bool used)
+{
+ struct pcb * const pcb = lwp_getpcb(l);
/*
* Enable SPE temporarily (and disable interrupts).
@@ -63,37 +84,30 @@
mtmsr((msr & ~PSL_EE) | PSL_SPV);
__asm volatile ("isync");
- if (ci->ci_veclwp != l) {
- struct pcb * const pcb = lwp_getpcb(l);
- /*
- * Save the existing state (if any).
- */
- vec_save_cpu(VEC_SAVE_AND_RELEASE);
+ /*
+ * Call an assembly routine to do load everything.
+ */
+ vec_load_from_vreg(&pcb->pcb_vr);
+ __asm volatile ("sync");
- /*
- * Call an assembly routine to do load everything.
- */
- vec_load_from_vreg(&pcb->pcb_vr);
-
- /*
- * Enable SPE when we return to user-mode (we overload the
- * ALTIVEC flags). Record the new ownership of the SPE unit.
- */
- ci->ci_veclwp = l;
- l->l_md.md_veccpu = ci;
- }
- __asm volatile ("sync");
- l->l_md.md_flags |= MDLWP_OWNVEC;
/*
* Restore MSR (turn off SPE)
*/
mtmsr(msr);
+ __asm volatile ("isync");
+
+ /*
+ * Note that vector has now been used.
+ */
+ l->l_md.md_flags |= MDLWP_USEDVEC;
}
void
-vec_save_cpu(enum vec_op op)
+vec_state_save(lwp_t *l)
{
+ struct pcb * const pcb = lwp_getpcb(l);
+
/*
* Turn on SPE, turn off interrupts.
*/
@@ -101,71 +115,27 @@
mtmsr((msr & ~PSL_EE) | PSL_SPV);
__asm volatile ("isync");
- struct cpu_info * const ci = curcpu();
- lwp_t * const l = ci->ci_veclwp;
-
- KASSERTMSG(l->l_md.md_veccpu == ci,
- ("%s: veccpu (%p) != ci (%p)\n", __func__, l->l_md.md_veccpu, ci));
- if (l->l_md.md_flags & MDLWP_OWNVEC) {
- struct pcb * const pcb = lwp_getpcb(l);
-
- /*
- * Save the vector state which is best done in assembly.
- */
- vec_unload_to_vreg(&pcb->pcb_vr);
-
- /*
- * Indicate that VEC unit is unloaded
- */
- l->l_md.md_flags &= ~MDLWP_OWNVEC;
-
- /*
- * If asked to, give up the VEC unit.
- */
- if (op == VEC_SAVE_AND_RELEASE)
- ci->ci_veclwp = ci->ci_data.cpu_idlelwp;
- }
+ /*
+ * Save the vector state which is best done in assembly.
+ */
+ vec_unload_to_vreg(&pcb->pcb_vr);
+ __asm volatile ("sync");
/*
* Restore MSR (turn off SPE)
*/
mtmsr(msr);
+ __asm volatile ("isync");
}
-/*
- * Save a lwp's SPE state to its PCB. The lwp must either be curlwp or traced
- * by curlwp (and stopped). (The point being that the lwp must not be onproc
- * on another CPU during this function).
- */
void
-vec_save_lwp(lwp_t *l, enum vec_op op)
+vec_state_release(lwp_t *l)
{
- struct cpu_info * const ci = curcpu();
-
- /*
- * If it's already in the PCB, there's nothing to do.
- */
- if ((l->l_md.md_flags & MDLWP_OWNVEC) == 0)
- return;
-
/*
- * If we simply need to discard the information, then don't
- * to save anything.
+ * Turn off SPV so the next SPE instruction will cause a
+ * SPE unavailable exception
*/
- if (op == VEC_DISCARD) {
- struct cpu_info * const veccpu = l->l_md.md_veccpu;
-#ifndef MULTIPROCESSOR
- KASSERT(ci == veccpu);
-#endif
- KASSERT(l == veccpu->ci_veclwp);
- KASSERT(l == curlwp || ci == veccpu);
- ci->ci_veclwp = ci->ci_data.cpu_idlelwp;
- atomic_and_uint(&l->l_md.md_flags, ~MDLWP_OWNVEC);
- return;
- }
-
- KASSERT(l == ci->ci_veclwp);
- vec_save_cpu(op);
+ l->l_md.md_utf->tf_srr1 &= ~PSL_SPV;
}
void
@@ -174,7 +144,9 @@
struct pcb * const pcb = lwp_getpcb(l);
const union __vr *vr = mcp->__vrf.__vrs;
- vec_save_lwp(l, VEC_DISCARD);
+ KASSERT(l == curlwp);
+
+ vec_save();
/* grab the accumulator */
pcb->pcb_vr.vreg[8][0] = vr->__vr32[2];
@@ -198,10 +170,12 @@
{
struct pcb * const pcb = lwp_getpcb(l);
- if ((l->l_md.md_flags & MDLWP_USEDVEC) == 0)
+ KASSERT(l == curlwp);
+
+ if (!vec_used_p(l))
return false;
- vec_save_lwp(l, VEC_SAVE);
+ vec_save();
mcp->__gregs[_REG_MSR] |= PSL_SPV;
diff -r cf0c3267cdc8 -r 2191d0d74c97 sys/arch/powerpc/booke/trap.c
--- a/sys/arch/powerpc/booke/trap.c Mon May 02 01:49:23 2011 +0000
+++ b/sys/arch/powerpc/booke/trap.c Mon May 02 02:01:32 2011 +0000
@@ -1,4 +1,4 @@
-/* $NetBSD: trap.c,v 1.5 2011/02/17 13:53:32 matt Exp $ */
+/* $NetBSD: trap.c,v 1.6 2011/05/02 02:01:32 matt Exp $ */
/*-
* Copyright (c) 2010, 2011 The NetBSD Foundation, Inc.
* All rights reserved.
@@ -39,7 +39,7 @@
#include <sys/cdefs.h>
-__KERNEL_RCSID(1, "$NetBSD: trap.c,v 1.5 2011/02/17 13:53:32 matt Exp $");
+__KERNEL_RCSID(1, "$NetBSD: trap.c,v 1.6 2011/05/02 02:01:32 matt Exp $");
#include <sys/param.h>
#include <sys/systm.h>
@@ -400,7 +400,7 @@
ci->ci_ev_vec.ev_count++;
#ifdef PPC_HAVE_SPE
- vec_enable();
+ vec_load();
return 0;
#else
KSI_INIT_TRAP(ksi);
diff -r cf0c3267cdc8 -r 2191d0d74c97 sys/arch/powerpc/conf/files.powerpc
--- a/sys/arch/powerpc/conf/files.powerpc Mon May 02 01:49:23 2011 +0000
+++ b/sys/arch/powerpc/conf/files.powerpc Mon May 02 02:01:32 2011 +0000
@@ -1,4 +1,4 @@
-# $NetBSD: files.powerpc,v 1.75 2011/04/26 15:51:24 joerg Exp $
+# $NetBSD: files.powerpc,v 1.76 2011/05/02 02:01:32 matt Exp $
defflag opt_altivec.h ALTIVEC K_ALTIVEC PPC_HAVE_SPE
defflag opt_openpic.h OPENPIC OPENPIC_SERIAL_MODE
@@ -35,6 +35,7 @@
file arch/powerpc/powerpc/db_disasm.c ddb
file arch/powerpc/powerpc/db_interface.c ddb | kgdb
file arch/powerpc/powerpc/db_trace.c ddb
+file arch/powerpc/powerpc/fpu.c
# IBM 4xx Family files (40x)
file arch/powerpc/ibm4xx/pmap.c ppc_ibm4xx
@@ -53,7 +54,6 @@
file arch/powerpc/oea/pmap64.c ppc_oea64
file arch/powerpc/oea/pmap64_bridge.c ppc_oea64_bridge
file arch/powerpc/oea/pmap_kernel.c ppc_oea | ppc_oea64 | ppc_oea64_bridge | ppc_oea601
-file arch/powerpc/powerpc/fpu.c ppc_oea | ppc_oea64 | ppc_oea64_bridge | ppc_oea601
file arch/powerpc/powerpc/trap.c ppc_oea | ppc_oea64 | ppc_oea64_bridge | ppc_oea601
# PPC BookE (MPC85xx) Family files
diff -r cf0c3267cdc8 -r 2191d0d74c97 sys/arch/powerpc/include/altivec.h
--- a/sys/arch/powerpc/include/altivec.h Mon May 02 01:49:23 2011 +0000
+++ b/sys/arch/powerpc/include/altivec.h Mon May 02 02:01:32 2011 +0000
@@ -1,4 +1,4 @@
-/* $NetBSD: altivec.h,v 1.13 2011/01/18 01:02:54 matt Exp $ */
+/* $NetBSD: altivec.h,v 1.14 2011/05/02 02:01:32 matt Exp $ */
/*-
* Copyright (c) 1999 The NetBSD Foundation, Inc.
@@ -36,24 +36,44 @@
#define VSCR_NJ 0x00010000 /* Non Java-IEEE-C9X FP mode */
#ifdef _KERNEL
+#include <sys/pcu.h>
#include <powerpc/mcontext.h>
-enum vec_op { VEC_SAVE, VEC_DISCARD, VEC_SAVE_AND_RELEASE };
struct lwp;
struct vreg;
struct trapframe;
-void vec_enable(void);
-void vec_save_cpu(enum vec_op);
-void vec_save_lwp(struct lwp *, enum vec_op);
Home |
Main Index |
Thread Index |
Old Index