Author: jhb
Date: Thu Mar  5 16:56:16 2009
New Revision: 189412
URL: http://svn.freebsd.org/changeset/base/189412

Log:
  A few cleanups to the FPU code on amd64:
  - fpudna() always returned 1 since amd64 CPUs always have FPUs.  Change
    the function to return void and adjust the calling code in trap() to
    assume the return 1 case is the only case.
  - Remove fpu_cleanstate_ready as it is always true when it is tested.
    Also, only initialize fpu_cleanstate when fpuinit() is called on the BSP.
  
  Reviewed by:  bde

Modified:
  head/sys/amd64/amd64/fpu.c
  head/sys/amd64/amd64/trap.c
  head/sys/amd64/include/fpu.h

Modified: head/sys/amd64/amd64/fpu.c
==============================================================================
--- head/sys/amd64/amd64/fpu.c  Thu Mar  5 16:52:50 2009        (r189411)
+++ head/sys/amd64/amd64/fpu.c  Thu Mar  5 16:56:16 2009        (r189412)
@@ -102,10 +102,11 @@ SYSCTL_INT(_hw, HW_FLOATINGPT, floatingp
     NULL, 1, "Floating point instructions executed in hardware");
 
 static struct savefpu          fpu_cleanstate;
-static bool_t                  fpu_cleanstate_ready;
 
 /*
- * Initialize floating point unit.
+ * Initialize the floating point unit.  On the boot CPU we generate a
+ * clean state that is used to initialize the floating point unit when
+ * it is first used by a process.
  */
 void
 fpuinit(void)
@@ -115,22 +116,22 @@ fpuinit(void)
        u_short control;
 
        savecrit = intr_disable();
-       PCPU_SET(fpcurthread, 0);
        stop_emulating();
        fninit();
        control = __INITIAL_FPUCW__;
        fldcw(&control);
        mxcsr = __INITIAL_MXCSR__;
        ldmxcsr(mxcsr);
-       fxsave(&fpu_cleanstate);
-       if (fpu_cleanstate.sv_env.en_mxcsr_mask)
-               cpu_mxcsr_mask = fpu_cleanstate.sv_env.en_mxcsr_mask;
-       else
-               cpu_mxcsr_mask = 0xFFBF;
+       if (PCPU_GET(cpuid) == 0) {
+               fxsave(&fpu_cleanstate);
+               if (fpu_cleanstate.sv_env.en_mxcsr_mask)
+                       cpu_mxcsr_mask = fpu_cleanstate.sv_env.en_mxcsr_mask;
+               else
+                       cpu_mxcsr_mask = 0xFFBF;
+               bzero(fpu_cleanstate.sv_fp, sizeof(fpu_cleanstate.sv_fp));
+               bzero(fpu_cleanstate.sv_xmm, sizeof(fpu_cleanstate.sv_xmm));
+       }
        start_emulating();
-       bzero(fpu_cleanstate.sv_fp, sizeof(fpu_cleanstate.sv_fp));
-       bzero(fpu_cleanstate.sv_xmm, sizeof(fpu_cleanstate.sv_xmm));
-       fpu_cleanstate_ready = 1;
        intr_restore(savecrit);
 }
 
@@ -384,8 +385,8 @@ fputrap()
 
 static int err_count = 0;
 
-int
-fpudna()
+void
+fpudna(void)
 {
        struct pcb *pcb;
        register_t s;
@@ -395,7 +396,7 @@ fpudna()
                printf("fpudna: fpcurthread == curthread %d times\n",
                    ++err_count);
                stop_emulating();
-               return (1);
+               return;
        }
        if (PCPU_GET(fpcurthread) != NULL) {
                printf("fpudna: fpcurthread = %p (%d), curthread = %p (%d)\n",
@@ -428,8 +429,6 @@ fpudna()
        } else
                fxrstor(&pcb->pcb_save);
        intr_restore(s);
-
-       return (1);
 }
 
 /*
@@ -457,10 +456,7 @@ fpugetregs(struct thread *td, struct sav
        register_t s;
 
        if ((td->td_pcb->pcb_flags & PCB_FPUINITDONE) == 0) {
-               if (fpu_cleanstate_ready)
-                       bcopy(&fpu_cleanstate, addr, sizeof(fpu_cleanstate));
-               else
-                       bzero(addr, sizeof(*addr));
+               bcopy(&fpu_cleanstate, addr, sizeof(fpu_cleanstate));
                return (_MC_FPOWNED_NONE);
        }
        s = intr_disable();

Modified: head/sys/amd64/amd64/trap.c
==============================================================================
--- head/sys/amd64/amd64/trap.c Thu Mar  5 16:52:50 2009        (r189411)
+++ head/sys/amd64/amd64/trap.c Thu Mar  5 16:56:16 2009        (r189412)
@@ -416,13 +416,8 @@ trap(struct trapframe *frame)
 
                case T_DNA:
                        /* transparent fault (due to context switch "late") */
-                       if (fpudna())
-                               goto userout;
-                       printf("pid %d killed due to lack of floating point\n",
-                               p->p_pid);
-                       i = SIGKILL;
-                       ucode = 0;
-                       break;
+                       fpudna();
+                       goto userout;
 
                case T_FPOPFLT:         /* FPU operand fetch fault */
                        ucode = ILL_COPROC;
@@ -450,11 +445,9 @@ trap(struct trapframe *frame)
                         * XXX this should be fatal unless the kernel has
                         * registered such use.
                         */
-                       if (fpudna()) {
-                               printf("fpudna in kernel mode!\n");
-                               goto out;
-                       }
-                       break;
+                       fpudna();
+                       printf("fpudna in kernel mode!\n");
+                       goto out;
 
                case T_STKFLT:          /* stack fault */
                        break;

Modified: head/sys/amd64/include/fpu.h
==============================================================================
--- head/sys/amd64/include/fpu.h        Thu Mar  5 16:52:50 2009        
(r189411)
+++ head/sys/amd64/include/fpu.h        Thu Mar  5 16:56:16 2009        
(r189412)
@@ -97,7 +97,7 @@ struct  savefpu {
 #define        __INITIAL_MXCSR_MASK__  0xFFBF
 
 #ifdef _KERNEL
-int    fpudna(void);
+void   fpudna(void);
 void   fpudrop(void);
 void   fpuexit(struct thread *td);
 int    fpuformat(void);
_______________________________________________
svn-src-all@freebsd.org mailing list
http://lists.freebsd.org/mailman/listinfo/svn-src-all
To unsubscribe, send any mail to "svn-src-all-unsubscr...@freebsd.org"

Reply via email to