Author: nwhitehorn
Date: Mon Nov 11 17:37:50 2013
New Revision: 258002
URL: http://svnweb.freebsd.org/changeset/base/258002

Log:
  Follow up r223485, which made AIM use the ABI thread pointer instead of
  PCPU fields for curthread, by doing the same to Book-E. This closes
  some potential races switching between CPUs. As a side effect, it turns out
  the AIM and Book-E swtch.S implementations were the same to within a few
  registers, so move that to powerpc/powerpc.
  
  MFC after: 3 months

Added:
  head/sys/powerpc/powerpc/swtch32.S
     - copied, changed from r257990, head/sys/powerpc/aim/swtch32.S
  head/sys/powerpc/powerpc/swtch64.S
     - copied unchanged from r257990, head/sys/powerpc/aim/swtch64.S
Deleted:
  head/sys/powerpc/aim/swtch32.S
  head/sys/powerpc/aim/swtch64.S
  head/sys/powerpc/booke/swtch.S
Modified:
  head/sys/conf/files.powerpc
  head/sys/powerpc/booke/locore.S
  head/sys/powerpc/booke/machdep.c
  head/sys/powerpc/booke/mp_cpudep.c
  head/sys/powerpc/booke/pmap.c
  head/sys/powerpc/booke/trap_subr.S
  head/sys/powerpc/include/pcpu.h

Modified: head/sys/conf/files.powerpc
==============================================================================
--- head/sys/conf/files.powerpc Mon Nov 11 17:07:02 2013        (r258001)
+++ head/sys/conf/files.powerpc Mon Nov 11 17:37:50 2013        (r258002)
@@ -96,8 +96,6 @@ powerpc/aim/moea64_if.m               optional        aim
 powerpc/aim/moea64_native.c    optional        aim
 powerpc/aim/mp_cpudep.c                optional        aim smp
 powerpc/aim/slb.c              optional        aim powerpc64
-powerpc/aim/swtch32.S          optional        aim powerpc
-powerpc/aim/swtch64.S          optional        aim powerpc64
 powerpc/aim/trap.c             optional        aim
 powerpc/aim/uma_machdep.c      optional        aim
 powerpc/booke/copyinout.c      optional        booke
@@ -108,7 +106,6 @@ powerpc/booke/machdep_e500.c        optional        bo
 powerpc/booke/mp_cpudep.c      optional        booke smp
 powerpc/booke/platform_bare.c  optional        booke
 powerpc/booke/pmap.c           optional        booke
-powerpc/booke/swtch.S          optional        booke
 powerpc/booke/trap.c           optional        booke
 powerpc/cpufreq/dfs.c          optional        cpufreq
 powerpc/cpufreq/pcr.c          optional        cpufreq aim
@@ -205,6 +202,8 @@ powerpc/powerpc/sc_machdep.c        optional        sc
 powerpc/powerpc/setjmp.S       standard
 powerpc/powerpc/sigcode32.S    optional        powerpc | compat_freebsd32
 powerpc/powerpc/sigcode64.S    optional        powerpc64
+powerpc/powerpc/swtch32.S      optional        powerpc
+powerpc/powerpc/swtch64.S      optional        powerpc64
 powerpc/powerpc/stack_machdep.c        optional        ddb | stack
 powerpc/powerpc/suswintr.c     standard
 powerpc/powerpc/syncicache.c   standard

Modified: head/sys/powerpc/booke/locore.S
==============================================================================
--- head/sys/powerpc/booke/locore.S     Mon Nov 11 17:07:02 2013        
(r258001)
+++ head/sys/powerpc/booke/locore.S     Mon Nov 11 17:37:50 2013        
(r258002)
@@ -738,8 +738,7 @@ ENTRY(icache_enable)
 setfault:
        mflr    %r0
        mfsprg0 %r4
-       lwz     %r4, PC_CURTHREAD(%r4)
-       lwz     %r4, TD_PCB(%r4)
+       lwz     %r4, TD_PCB(%r2)
        stw     %r3, PCB_ONFAULT(%r4)
        mfcr    %r10
        mfctr   %r11

Modified: head/sys/powerpc/booke/machdep.c
==============================================================================
--- head/sys/powerpc/booke/machdep.c    Mon Nov 11 17:07:02 2013        
(r258001)
+++ head/sys/powerpc/booke/machdep.c    Mon Nov 11 17:37:50 2013        
(r258002)
@@ -409,6 +409,11 @@ booke_init(uint32_t arg1, uint32_t arg2)
        pc = &__pcpu[0];
        pcpu_init(pc, 0, sizeof(struct pcpu));
        pc->pc_curthread = &thread0;
+#ifdef __powerpc64__
+       __asm __volatile("mr 13,%0" :: "r"(pc->pc_curthread));
+#else
+       __asm __volatile("mr 2,%0" :: "r"(pc->pc_curthread));
+#endif
        __asm __volatile("mtsprg 0, %0" :: "r"(pc));
 
        /* Initialize system mutexes. */

Modified: head/sys/powerpc/booke/mp_cpudep.c
==============================================================================
--- head/sys/powerpc/booke/mp_cpudep.c  Mon Nov 11 17:07:02 2013        
(r258001)
+++ head/sys/powerpc/booke/mp_cpudep.c  Mon Nov 11 17:37:50 2013        
(r258002)
@@ -71,6 +71,11 @@ cpudep_ap_bootstrap()
 
        /* Assign pcpu fields, return ptr to this AP's idle thread kstack */
        pcpup->pc_curthread = pcpup->pc_idlethread;
+#ifdef __powerpc64__
+       __asm __volatile("mr 13,%0" :: "r"(pcpup->pc_curthread));
+#else
+       __asm __volatile("mr 2,%0" :: "r"(pcpup->pc_curthread));
+#endif
        pcpup->pc_curpcb = pcpup->pc_curthread->td_pcb;
        sp = pcpup->pc_curpcb->pcb_sp;
 

Modified: head/sys/powerpc/booke/pmap.c
==============================================================================
--- head/sys/powerpc/booke/pmap.c       Mon Nov 11 17:07:02 2013        
(r258001)
+++ head/sys/powerpc/booke/pmap.c       Mon Nov 11 17:37:50 2013        
(r258002)
@@ -100,8 +100,6 @@ __FBSDID("$FreeBSD$");
 
 #define TODO                   panic("%s: not implemented", __func__);
 
-extern struct mtx sched_lock;
-
 extern int dumpsys_minidump;
 
 extern unsigned char _etext[];
@@ -1906,7 +1904,7 @@ mmu_booke_activate(mmu_t mmu, struct thr
 
        KASSERT((pmap != kernel_pmap), ("mmu_booke_activate: kernel_pmap!"));
 
-       mtx_lock_spin(&sched_lock);
+       sched_pin();
 
        cpuid = PCPU_GET(cpuid);
        CPU_SET_ATOMIC(cpuid, &pmap->pm_active);
@@ -1919,7 +1917,7 @@ mmu_booke_activate(mmu_t mmu, struct thr
        mtspr(SPR_PID0, pmap->pm_tid[cpuid]);
        __asm __volatile("isync");
 
-       mtx_unlock_spin(&sched_lock);
+       sched_unpin();
 
        CTR3(KTR_PMAP, "%s: e (tid = %d for '%s')", __func__,
            pmap->pm_tid[PCPU_GET(cpuid)], td->td_proc->p_comm);

Modified: head/sys/powerpc/booke/trap_subr.S
==============================================================================
--- head/sys/powerpc/booke/trap_subr.S  Mon Nov 11 17:07:02 2013        
(r258001)
+++ head/sys/powerpc/booke/trap_subr.S  Mon Nov 11 17:37:50 2013        
(r258002)
@@ -219,7 +219,8 @@
        lwz     %r30, (savearea+CPUSAVE_SRR0)(%r2);                     \
        lwz     %r31, (savearea+CPUSAVE_SRR1)(%r2);                     \
        stw     %r30, FRAME_SRR0+8(%r1);                                \
-       stw     %r31, FRAME_SRR1+8(%r1)
+       stw     %r31, FRAME_SRR1+8(%r1);                                \
+       lwz     %r2,PC_CURTHREAD(%r2)   /* set curthread pointer */
 
 /*
  *
@@ -734,7 +735,8 @@ interrupt_vector_top:
 INTERRUPT(int_debug)
        STANDARD_CRIT_PROLOG(SPR_SPRG2, PC_BOOKE_CRITSAVE, SPR_CSRR0, SPR_CSRR1)
        FRAME_SETUP(SPR_SPRG2, PC_BOOKE_CRITSAVE, EXC_DEBUG)
-       lwz     %r3, (PC_BOOKE_CRITSAVE+CPUSAVE_SRR0)(%r2);
+       GET_CPUINFO(%r3)
+       lwz     %r3, (PC_BOOKE_CRITSAVE+CPUSAVE_SRR0)(%r3)
        lis     %r4, interrupt_vector_base@ha
        addi    %r4, %r4, interrupt_vector_base@l
        cmplw   cr0, %r3, %r4
@@ -748,9 +750,10 @@ INTERRUPT(int_debug)
        rlwinm  %r3, %r3, 0, 23, 21
        stw     %r3, FRAME_SRR1+8(%r1);
        /* Restore srr0 and srr1 as they could have been clobbered. */
-       lwz     %r3, (PC_BOOKE_CRITSAVE+CPUSAVE_SRR0+8)(%r2);
+       GET_CPUINFO(%r4)
+       lwz     %r3, (PC_BOOKE_CRITSAVE+CPUSAVE_SRR0+8)(%r4);
        mtspr   SPR_SRR0, %r3
-       lwz     %r4, (PC_BOOKE_CRITSAVE+CPUSAVE_SRR1+8)(%r2);
+       lwz     %r4, (PC_BOOKE_CRITSAVE+CPUSAVE_SRR1+8)(%r4);
        mtspr   SPR_SRR1, %r4
        b       9f
 1:

Modified: head/sys/powerpc/include/pcpu.h
==============================================================================
--- head/sys/powerpc/include/pcpu.h     Mon Nov 11 17:07:02 2013        
(r258001)
+++ head/sys/powerpc/include/pcpu.h     Mon Nov 11 17:37:50 2013        
(r258002)
@@ -135,7 +135,6 @@ struct pmap;
 
 #define pcpup  ((struct pcpu *) powerpc_get_pcpup())
 
-#ifdef AIM /* Book-E not yet adapted */
 static __inline __pure2 struct thread *
 __curthread(void)
 {
@@ -148,7 +147,6 @@ __curthread(void)
        return (td);
 }
 #define curthread (__curthread())
-#endif
 
 #define        PCPU_GET(member)        (pcpup->pc_ ## member)
 

Copied and modified: head/sys/powerpc/powerpc/swtch32.S (from r257990, 
head/sys/powerpc/aim/swtch32.S)
==============================================================================
--- head/sys/powerpc/aim/swtch32.S      Mon Nov 11 14:08:25 2013        
(r257990, copy source)
+++ head/sys/powerpc/powerpc/swtch32.S  Mon Nov 11 17:37:50 2013        
(r258002)
@@ -64,6 +64,7 @@
 #include <machine/trap.h>
 #include <machine/param.h>
 #include <machine/asm.h>
+#include <machine/spr.h>
 
 /*
  * void cpu_throw(struct thread *old, struct thread *new)
@@ -88,6 +89,14 @@ ENTRY(cpu_switch)
        stw     %r16,PCB_CR(%r6)
        mflr    %r16                    /* Save the link register */
        stw     %r16,PCB_LR(%r6)
+#ifdef BOOKE
+       mfctr   %r16
+       stw     %r16,PCB_BOOKE_CTR(%r6)
+       mfxer   %r16
+       stw     %r16,PCB_BOOKE_XER(%r6)
+       mfspr   %r16,SPR_DBCR0
+       stw     %r16,PCB_BOOKE_DBCR0(%r6)
+#endif
        stw     %r1,PCB_SP(%r6)         /* Save the stack pointer */
 
        mr      %r14,%r3                /* Copy the old thread ptr... */
@@ -95,6 +104,7 @@ ENTRY(cpu_switch)
        mr      %r16,%r5                /* and the new lock */
        mr      %r17,%r6                /* and the PCB */
        
+#ifdef AIM
        lwz     %r7,PCB_FLAGS(%r17)
        /* Save FPU context if needed */
        andi.   %r7, %r7, PCB_FPU
@@ -110,6 +120,7 @@ ENTRY(cpu_switch)
        bl      save_vec
        
 .L2:
+#endif
        mr      %r3,%r14                /* restore old thread ptr */
        bl      pmap_deactivate         /* Deactivate the current pmap */
 
@@ -136,6 +147,7 @@ blocked_loop:
        mr      %r3,%r2                 /* Get new thread ptr */
        bl      pmap_activate           /* Activate the new address space */
 
+#ifdef AIM
        lwz     %r6, PCB_FLAGS(%r17)
        /* Restore FPU context if needed */
        andi.   %r6, %r6, PCB_FPU
@@ -151,18 +163,29 @@ blocked_loop:
        mr      %r3,%r2                 /* Pass curthread to enable_vec */
        bl      enable_vec
 
-       /* thread to restore is in r3 */
 .L4:
+#endif
+       /* thread to restore is in r3 */
        mr      %r3,%r17                /* Recover PCB ptr */
        lmw     %r12,PCB_CONTEXT(%r3)   /* Load the non-volatile GP regs */
        lwz     %r5,PCB_CR(%r3)         /* Load the condition register */
        mtcr    %r5
        lwz     %r5,PCB_LR(%r3)         /* Load the link register */
        mtlr    %r5
+#ifdef AIM
        lwz     %r5,PCB_AIM_USR_VSID(%r3) /* Load the USER_SR segment reg */
        isync
        mtsr    USER_SR,%r5
        isync
+#endif
+#ifdef BOOKE
+       lwz     %r5,PCB_BOOKE_CTR(%r3)
+       mtctr   %r5
+       lwz     %r5,PCB_BOOKE_XER(%r3)
+       mtctr   %r5
+       lwz     %r5,PCB_BOOKE_DBCR0(%r3)
+       mtspr   SPR_DBCR0,%r5
+#endif
        lwz     %r1,PCB_SP(%r3)         /* Load the stack pointer */
        /*
         * Perform a dummy stwcx. to clear any reservations we may have

Copied: head/sys/powerpc/powerpc/swtch64.S (from r257990, 
head/sys/powerpc/aim/swtch64.S)
==============================================================================
--- /dev/null   00:00:00 1970   (empty, because file is newly added)
+++ head/sys/powerpc/powerpc/swtch64.S  Mon Nov 11 17:37:50 2013        
(r258002, copy of r257990, head/sys/powerpc/aim/swtch64.S)
@@ -0,0 +1,287 @@
+/* $FreeBSD$ */
+/* $NetBSD: locore.S,v 1.24 2000/05/31 05:09:17 thorpej Exp $ */
+
+/*-
+ * Copyright (C) 2001 Benno Rice
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ *
+ * THIS SOFTWARE IS PROVIDED BY Benno Rice ``AS IS'' AND ANY EXPRESS OR
+ * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
+ * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
+ * IN NO EVENT SHALL TOOLS GMBH BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+ * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
+ * OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
+ * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
+ * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
+ * ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+*/
+/*-
+ * Copyright (C) 1995, 1996 Wolfgang Solfrank.
+ * Copyright (C) 1995, 1996 TooLs GmbH.
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions
+ * are met:
+ * 1. Redistributions of source code must retain the above copyright
+ *    notice, this list of conditions and the following disclaimer.
+ * 2. Redistributions in binary form must reproduce the above copyright
+ *    notice, this list of conditions and the following disclaimer in the
+ *    documentation and/or other materials provided with the distribution.
+ * 3. All advertising materials mentioning features or use of this software
+ *    must display the following acknowledgement:
+ *     This product includes software developed by TooLs GmbH.
+ * 4. The name of TooLs GmbH may not be used to endorse or promote products
+ *    derived from this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY TOOLS GMBH ``AS IS'' AND ANY EXPRESS OR
+ * IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES
+ * OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE DISCLAIMED.
+ * IN NO EVENT SHALL TOOLS GMBH BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+ * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO,
+ * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS;
+ * OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY,
+ * WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR
+ * OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF
+ * ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#include "assym.s"
+#include "opt_sched.h"
+
+#include <sys/syscall.h>
+
+#include <machine/trap.h>
+#include <machine/param.h>
+#include <machine/asm.h>
+
+/*
+ * void cpu_throw(struct thread *old, struct thread *new)
+ */
+ENTRY(cpu_throw)
+       mr      %r13, %r4
+       b       cpu_switchin
+
+/*
+ * void cpu_switch(struct thread *old,
+ *                struct thread *new,
+ *                struct mutex *mtx); 
+ *
+ * Switch to a new thread saving the current state in the old thread.
+ */
+ENTRY(cpu_switch)
+       ld      %r6,TD_PCB(%r3)         /* Get the old thread's PCB ptr */
+       std     %r12,PCB_CONTEXT(%r6)   /* Save the non-volatile GP regs.
+                                          These can now be used for scratch */
+       std     %r14,PCB_CONTEXT+2*8(%r6)       
+       std     %r15,PCB_CONTEXT+3*8(%r6)       
+       std     %r16,PCB_CONTEXT+4*8(%r6)       
+       std     %r17,PCB_CONTEXT+5*8(%r6)       
+       std     %r18,PCB_CONTEXT+6*8(%r6)       
+       std     %r19,PCB_CONTEXT+7*8(%r6)       
+       std     %r20,PCB_CONTEXT+8*8(%r6)       
+       std     %r21,PCB_CONTEXT+9*8(%r6)       
+       std     %r22,PCB_CONTEXT+10*8(%r6)      
+       std     %r23,PCB_CONTEXT+11*8(%r6)      
+       std     %r24,PCB_CONTEXT+12*8(%r6)      
+       std     %r25,PCB_CONTEXT+13*8(%r6)      
+       std     %r26,PCB_CONTEXT+14*8(%r6)      
+       std     %r27,PCB_CONTEXT+15*8(%r6)      
+       std     %r28,PCB_CONTEXT+16*8(%r6)      
+       std     %r29,PCB_CONTEXT+17*8(%r6)      
+       std     %r30,PCB_CONTEXT+18*8(%r6)      
+       std     %r31,PCB_CONTEXT+19*8(%r6)      
+
+       mfcr    %r16                    /* Save the condition register */
+       std     %r16,PCB_CR(%r6)
+       mflr    %r16                    /* Save the link register */
+       std     %r16,PCB_LR(%r6)
+       std     %r1,PCB_SP(%r6)         /* Save the stack pointer */
+       std     %r2,PCB_TOC(%r6)        /* Save the TOC pointer */
+       
+       mr      %r14,%r3                /* Copy the old thread ptr... */
+       mr      %r13,%r4                /* and the new thread ptr in curthread*/
+       mr      %r16,%r5                /* and the new lock */
+       mr      %r17,%r6                /* and the PCB */
+       
+       stdu    %r1,-48(%r1)
+
+       lwz     %r7,PCB_FLAGS(%r17)
+       /* Save FPU context if needed */
+       andi.   %r7, %r7, PCB_FPU
+       beq     .L1
+       bl      save_fpu
+       nop
+
+.L1:
+       mr      %r3,%r14                /* restore old thread ptr */
+       lwz     %r7,PCB_FLAGS(%r17)
+       /* Save Altivec context if needed */
+       andi.   %r7, %r7, PCB_VEC
+       beq     .L2
+       bl      save_vec
+       nop
+       
+.L2:
+       mr      %r3,%r14                /* restore old thread ptr */
+       bl      pmap_deactivate /* Deactivate the current pmap */
+       nop
+
+       addi    %r1,%r1,48
+
+       sync                            /* Make sure all of that finished */
+       std     %r16,TD_LOCK(%r14)      /* ULE: update old thread's lock */
+
+cpu_switchin:
+#if defined(SMP) && defined(SCHED_ULE)
+       /* Wait for the new thread to become unblocked */
+       lis     %r6,blocked_lock@ha
+       addi    %r6,%r6,blocked_lock@l
+blocked_loop:
+       ld      %r7,TD_LOCK(%r13)
+       cmpd    %r6,%r7 
+       beq-    blocked_loop
+       isync
+#endif
+
+       mfsprg  %r7,0                   /* Get the pcpu pointer */
+       std     %r13,PC_CURTHREAD(%r7)  /* Store new current thread */
+       ld      %r17,TD_PCB(%r13)       /* Store new current PCB */
+       std     %r17,PC_CURPCB(%r7)
+
+       stdu    %r1,-48(%r1)
+
+       mr      %r3,%r13                /* Get new thread ptr */
+       bl      pmap_activate           /* Activate the new address space */
+       nop
+
+       lwz     %r6, PCB_FLAGS(%r17)
+       /* Restore FPU context if needed */
+       andi.   %r6, %r6, PCB_FPU
+       beq     .L3
+       mr      %r3,%r13                /* Pass curthread to enable_fpu */
+       bl      enable_fpu
+       nop
+
+.L3:
+       lwz     %r6, PCB_FLAGS(%r17)
+       /* Restore Altivec context if needed */
+       andi.   %r6, %r6, PCB_VEC
+       beq     .L4
+       mr      %r3,%r13                /* Pass curthread to enable_vec */
+       bl      enable_vec
+       nop
+
+       /* thread to restore is in r3 */
+.L4:
+       addi    %r1,%r1,48
+       mr      %r3,%r17                /* Recover PCB ptr */
+       ld      %r12,PCB_CONTEXT(%r3)   /* Load the non-volatile GP regs. */
+       ld      %r14,PCB_CONTEXT+2*8(%r3)       
+       ld      %r15,PCB_CONTEXT+3*8(%r3)       
+       ld      %r16,PCB_CONTEXT+4*8(%r3)       
+       ld      %r17,PCB_CONTEXT+5*8(%r3)       
+       ld      %r18,PCB_CONTEXT+6*8(%r3)       
+       ld      %r19,PCB_CONTEXT+7*8(%r3)       
+       ld      %r20,PCB_CONTEXT+8*8(%r3)       
+       ld      %r21,PCB_CONTEXT+9*8(%r3)       
+       ld      %r22,PCB_CONTEXT+10*8(%r3)      
+       ld      %r23,PCB_CONTEXT+11*8(%r3)      
+       ld      %r24,PCB_CONTEXT+12*8(%r3)      
+       ld      %r25,PCB_CONTEXT+13*8(%r3)      
+       ld      %r26,PCB_CONTEXT+14*8(%r3)      
+       ld      %r27,PCB_CONTEXT+15*8(%r3)      
+       ld      %r28,PCB_CONTEXT+16*8(%r3)
+       ld      %r29,PCB_CONTEXT+17*8(%r3)      
+       ld      %r30,PCB_CONTEXT+18*8(%r3)      
+       ld      %r31,PCB_CONTEXT+19*8(%r3)      
+       ld      %r5,PCB_CR(%r3)         /* Load the condition register */
+       mtcr    %r5
+       ld      %r5,PCB_LR(%r3)         /* Load the link register */
+       mtlr    %r5
+       ld      %r1,PCB_SP(%r3)         /* Load the stack pointer */
+       ld      %r2,PCB_TOC(%r3)        /* Load the TOC pointer */
+
+       lis     %r5,USER_ADDR@highesta  /* Load the copyin/out segment reg */
+       ori     %r5,%r5,USER_ADDR@highera
+       sldi    %r5,%r5,32
+       oris    %r5,%r5,USER_ADDR@ha
+       isync
+       slbie   %r5
+       lis     %r6,USER_SLB_SLBE@highesta
+       ori     %r6,%r6,USER_SLB_SLBE@highera
+       sldi    %r6,%r6,32
+       oris    %r6,%r6,USER_SLB_SLBE@ha
+       ori     %r6,%r6,USER_SLB_SLBE@l
+       ld      %r5,PCB_AIM_USR_VSID(%r3)
+       slbmte  %r5,%r6
+       isync
+
+       /*
+        * Perform a dummy stdcx. to clear any reservations we may have
+        * inherited from the previous thread. It doesn't matter if the
+        * stdcx succeeds or not. pcb_context[0] can be clobbered.
+        */
+       stdcx.  %r1, 0, %r3
+       blr
+
+/*
+ * savectx(pcb)
+ * Update pcb, saving current processor state
+ */
+ENTRY(savectx)
+       std     %r12,PCB_CONTEXT(%r3)   /* Save the non-volatile GP regs. */
+       std     %r13,PCB_CONTEXT+1*8(%r3)       
+       std     %r14,PCB_CONTEXT+2*8(%r3)       
+       std     %r15,PCB_CONTEXT+3*8(%r3)       
+       std     %r16,PCB_CONTEXT+4*8(%r3)       
+       std     %r17,PCB_CONTEXT+5*8(%r3)       
+       std     %r18,PCB_CONTEXT+6*8(%r3)       
+       std     %r19,PCB_CONTEXT+7*8(%r3)       
+       std     %r20,PCB_CONTEXT+8*8(%r3)       
+       std     %r21,PCB_CONTEXT+9*8(%r3)       
+       std     %r22,PCB_CONTEXT+10*8(%r3)      
+       std     %r23,PCB_CONTEXT+11*8(%r3)      
+       std     %r24,PCB_CONTEXT+12*8(%r3)      
+       std     %r25,PCB_CONTEXT+13*8(%r3)      
+       std     %r26,PCB_CONTEXT+14*8(%r3)      
+       std     %r27,PCB_CONTEXT+15*8(%r3)      
+       std     %r28,PCB_CONTEXT+16*8(%r3)
+       std     %r29,PCB_CONTEXT+17*8(%r3)      
+       std     %r30,PCB_CONTEXT+18*8(%r3)      
+       std     %r31,PCB_CONTEXT+19*8(%r3)      
+
+       mfcr    %r4                     /* Save the condition register */
+       std     %r4,PCB_CR(%r3)
+       std     %r2,PCB_TOC(%r3)        /* Save the TOC pointer */
+       blr
+
+/*
+ * fork_trampoline()
+ * Set up the return from cpu_fork()
+ */
+
+ENTRY_NOPROF(fork_trampoline)
+       ld      %r3,CF_FUNC(%r1)
+       ld      %r4,CF_ARG0(%r1)
+       ld      %r5,CF_ARG1(%r1)
+
+       stdu    %r1,-48(%r1)
+       bl      fork_exit
+       nop
+       addi    %r1,%r1,48+CF_SIZE-FSP  /* Allow 8 bytes in front of
+                                          trapframe to simulate FRAME_SETUP
+                                          does when allocating space for
+                                          a frame pointer/saved LR */
+       b       trapexit
+       nop
_______________________________________________
[email protected] mailing list
http://lists.freebsd.org/mailman/listinfo/svn-src-head
To unsubscribe, send any mail to "[email protected]"

Reply via email to