Date: Wed, 23 Jun 2010 11:12:59 +0000 (UTC) From: Konstantin Belousov <kib@FreeBSD.org> To: src-committers@freebsd.org, svn-src-all@freebsd.org, svn-src-head@freebsd.org Subject: svn commit: r209461 - in head/sys: i386/i386 i386/include i386/isa kern pc98/include Message-ID: <201006231112.o5NBCxml047925@svn.freebsd.org>
next in thread | raw e-mail | index | archive | help
Author: kib Date: Wed Jun 23 11:12:58 2010 New Revision: 209461 URL: http://svn.freebsd.org/changeset/base/209461 Log: Remove the support for int13 FPU exception reporting on i386. It is believed that all 486-class CPUs FreeBSD is capable to run on, either have no FPU and cannot use external coprocessor, or have FPU on the package and can use #MF. Reviewed by: bde Tested by: pho (previous version) Modified: head/sys/i386/i386/vm_machdep.c head/sys/i386/include/npx.h head/sys/i386/include/pcb.h head/sys/i386/isa/npx.c head/sys/kern/subr_trap.c head/sys/pc98/include/npx.h Modified: head/sys/i386/i386/vm_machdep.c ============================================================================== --- head/sys/i386/i386/vm_machdep.c Wed Jun 23 10:40:28 2010 (r209460) +++ head/sys/i386/i386/vm_machdep.c Wed Jun 23 11:12:58 2010 (r209461) @@ -441,7 +441,7 @@ cpu_set_upcall(struct thread *td, struct * values here. */ bcopy(td0->td_pcb, pcb2, sizeof(*pcb2)); - pcb2->pcb_flags &= ~(PCB_NPXTRAP|PCB_NPXINITDONE|PCB_NPXUSERINITDONE); + pcb2->pcb_flags &= ~(PCB_NPXINITDONE | PCB_NPXUSERINITDONE); pcb2->pcb_save = &pcb2->pcb_user_save; /* Modified: head/sys/i386/include/npx.h ============================================================================== --- head/sys/i386/include/npx.h Wed Jun 23 10:40:28 2010 (r209460) +++ head/sys/i386/include/npx.h Wed Jun 23 11:12:58 2010 (r209461) @@ -138,11 +138,6 @@ union savefpu { #ifdef _KERNEL -#define IO_NPX 0x0F0 /* Numeric Coprocessor */ -#define IO_NPXSIZE 16 /* 80387/80487 NPX registers */ - -#define IRQ_NPX 13 - struct fpu_kern_ctx { union savefpu hwstate; union savefpu *prev; @@ -152,9 +147,6 @@ struct fpu_kern_ctx { #define PCB_USER_FPU(pcb) (((pcb)->pcb_flags & PCB_KERNNPX) == 0) -/* full reset on some systems, NOP on others */ -#define npx_full_reset() outb(IO_NPX + 1, 0) - int npxdna(void); void npxdrop(void); void npxexit(struct thread *td); Modified: head/sys/i386/include/pcb.h ============================================================================== --- head/sys/i386/include/pcb.h Wed Jun 23 10:40:28 2010 (r209460) +++ head/sys/i386/include/pcb.h Wed Jun 23 11:12:58 2010 (r209461) @@ -65,7 +65,6 @@ struct pcb { u_int pcb_flags; #define FP_SOFTFP 0x01 /* process using software fltng pnt emulator */ #define PCB_DBREGS 0x02 /* process using debug registers */ -#define PCB_NPXTRAP 0x04 /* npx trap pending */ #define PCB_NPXINITDONE 0x08 /* fpu state is initialized */ #define PCB_VM86CALL 0x10 /* in vm86 call */ #define PCB_NPXUSERINITDONE 0x20 /* user fpu state is initialized */ Modified: head/sys/i386/isa/npx.c ============================================================================== --- head/sys/i386/isa/npx.c Wed Jun 23 10:40:28 2010 (r209460) +++ head/sys/i386/isa/npx.c Wed Jun 23 11:12:58 2010 (r209461) @@ -161,21 +161,15 @@ static void fpusave(union savefpu *); static void fpurstor(union savefpu *); static int npx_attach(device_t dev); static void npx_identify(driver_t *driver, device_t parent); -static int npx_intr(void *); static int npx_probe(device_t dev); -int hw_float; /* XXX currently just alias for npx_exists */ +int hw_float; SYSCTL_INT(_hw, HW_FLOATINGPT, floatingpoint, CTLFLAG_RD, &hw_float, 0, "Floating point instructions executed in hardware"); -static volatile u_int npx_intrs_while_probing; static volatile u_int npx_traps_while_probing; - static union savefpu npx_initialstate; -static bool_t npx_ex16; -static bool_t npx_exists; -static bool_t npx_irq13; alias_for_inthand_t probetrap; __asm(" \n\ @@ -205,58 +199,14 @@ npx_identify(driver, parent) } /* - * Do minimal handling of npx interrupts to convert them to traps. - */ -static int -npx_intr(dummy) - void *dummy; -{ - struct thread *td; - - npx_intrs_while_probing++; - - /* - * The BUSY# latch must be cleared in all cases so that the next - * unmasked npx exception causes an interrupt. - */ - outb(IO_NPX, 0); - - /* - * fpcurthread is normally non-null here. In that case, schedule an - * AST to finish the exception handling in the correct context - * (this interrupt may occur after the thread has entered the - * kernel via a syscall or an interrupt). Otherwise, the npx - * state of the thread that caused this interrupt must have been - * pushed to the thread's pcb, and clearing of the busy latch - * above has finished the (essentially null) handling of this - * interrupt. Control will eventually return to the instruction - * that caused it and it will repeat. We will eventually (usually - * soon) win the race to handle the interrupt properly. - */ - td = PCPU_GET(fpcurthread); - if (td != NULL) { - td->td_pcb->pcb_flags |= PCB_NPXTRAP; - thread_lock(td); - td->td_flags |= TDF_ASTPENDING; - thread_unlock(td); - } - return (FILTER_HANDLED); -} - -/* * Probe routine. Set flags to tell npxattach() what to do. Set up an * interrupt handler if npx needs to use interrupts. */ static int -npx_probe(dev) - device_t dev; +npx_probe(device_t dev) { struct gate_descriptor save_idt_npxtrap; - struct resource *ioport_res, *irq_res; - void *irq_cookie; - int ioport_rid, irq_num, irq_rid; - u_short control; - u_short status; + u_short control, status; device_set_desc(dev, "math processor"); @@ -266,8 +216,7 @@ npx_probe(dev) * common case right away. */ if (cpu_feature & CPUID_FPU) { - hw_float = npx_exists = 1; - npx_ex16 = 1; + hw_float = 1; device_quiet(dev); return (0); } @@ -275,28 +224,6 @@ npx_probe(dev) save_idt_npxtrap = idt[IDT_MF]; setidt(IDT_MF, probetrap, SDT_SYS386TGT, SEL_KPL, GSEL(GCODE_SEL, SEL_KPL)); - ioport_rid = 0; - ioport_res = bus_alloc_resource(dev, SYS_RES_IOPORT, &ioport_rid, - IO_NPX, IO_NPX + IO_NPXSIZE - 1, IO_NPXSIZE, RF_ACTIVE); - if (ioport_res == NULL) - panic("npx: can't get ports"); - if (resource_int_value("npx", 0, "irq", &irq_num) != 0) - irq_num = IRQ_NPX; - irq_rid = 0; - irq_res = bus_alloc_resource(dev, SYS_RES_IRQ, &irq_rid, irq_num, - irq_num, 1, RF_ACTIVE); - if (irq_res != NULL) { - if (bus_setup_intr(dev, irq_res, INTR_TYPE_MISC, - npx_intr, NULL, NULL, &irq_cookie) != 0) - panic("npx: can't create intr"); - } - - /* - * Partially reset the coprocessor, if any. Some BIOS's don't reset - * it after a warm boot. - */ - npx_full_reset(); - outb(IO_NPX, 0); /* * Don't trap while we're probing. @@ -317,9 +244,6 @@ npx_probe(dev) */ DELAY(1000); /* wait for any IRQ13 */ #ifdef DIAGNOSTIC - if (npx_intrs_while_probing != 0) - printf("fninit caused %u bogus npx interrupt(s)\n", - npx_intrs_while_probing); if (npx_traps_while_probing != 0) printf("fninit caused %u bogus npx trap(s)\n", npx_traps_while_probing); @@ -336,7 +260,6 @@ npx_probe(dev) control = 0x5a5a; fnstcw(&control); if ((control & 0x1f3f) == 0x033f) { - hw_float = npx_exists = 1; /* * We have an npx, now divide by 0 to see if exception * 16 works. @@ -348,70 +271,46 @@ npx_probe(dev) * FPU error signal doesn't work on some CPU * accelerator board. */ - npx_ex16 = 1; + hw_float = 1; return (0); #endif - npx_traps_while_probing = npx_intrs_while_probing = 0; + npx_traps_while_probing = 0; fp_divide_by_0(); - DELAY(1000); /* wait for any IRQ13 */ if (npx_traps_while_probing != 0) { /* * Good, exception 16 works. */ - npx_ex16 = 1; - goto no_irq13; - } - if (npx_intrs_while_probing != 0) { - /* - * Bad, we are stuck with IRQ13. - */ - npx_irq13 = 1; - idt[IDT_MF] = save_idt_npxtrap; -#ifdef SMP - if (mp_ncpus > 1) - panic("npx0 cannot use IRQ 13 on an SMP system"); -#endif - return (0); + hw_float = 1; + goto cleanup; } - /* - * Worse, even IRQ13 is broken. - */ + device_printf(dev, + "FPU does not use exception 16 for error reporting\n"); + goto cleanup; } } - /* Probe failed. Floating point simply won't work. */ + /* + * Probe failed. Floating point simply won't work. + * Notify user and disable FPU/MMX/SSE instruction execution. + */ device_printf(dev, "WARNING: no FPU!\n"); + __asm __volatile("smsw %%ax; orb %0,%%al; lmsw %%ax" : : + "n" (CR0_EM | CR0_MP) : "ax"); - /* FALLTHROUGH */ -no_irq13: +cleanup: idt[IDT_MF] = save_idt_npxtrap; - if (irq_res != NULL) { - bus_teardown_intr(dev, irq_res, irq_cookie); - bus_release_resource(dev, SYS_RES_IRQ, irq_rid, irq_res); - } - bus_release_resource(dev, SYS_RES_IOPORT, ioport_rid, ioport_res); - return (npx_exists ? 0 : ENXIO); + return (hw_float ? 0 : ENXIO); } /* * Attach routine - announce which it is, and wire into system */ static int -npx_attach(dev) - device_t dev; +npx_attach(device_t dev) { - int flags; register_t s; - flags = device_get_flags(dev); - - if (npx_irq13) - device_printf(dev, "IRQ 13 interface\n"); - else if (!device_is_quiet(dev) || bootverbose) - device_printf(dev, "INT 16 interface\n"); - npxinit(); - s = intr_disable(); stop_emulating(); fpusave(&npx_initialstate); @@ -447,7 +346,7 @@ npxinit(void) register_t savecrit; u_short control; - if (!npx_exists) + if (!hw_float) return; /* * fninit has the same h/w bugs as fnsave. Use the detoxified @@ -482,7 +381,7 @@ npxexit(td) npxsave(PCPU_GET(curpcb)->pcb_save); intr_restore(savecrit); #ifdef NPX_DEBUG - if (npx_exists) { + if (hw_float) { u_int masked_exceptions; masked_exceptions = GET_FPU_CW(td) & GET_FPU_SW(td) & 0x7f; @@ -503,7 +402,7 @@ int npxformat() { - if (!npx_exists) + if (!hw_float) return (_MC_FPFMT_NODEV); #ifdef CPU_ENABLE_SSE if (cpu_fxsr) @@ -706,9 +605,9 @@ npxtrap() register_t savecrit; u_short control, status; - if (!npx_exists) { - printf("npxtrap: fpcurthread = %p, curthread = %p, npx_exists = %d\n", - PCPU_GET(fpcurthread), curthread, npx_exists); + if (!hw_float) { + printf("npxtrap: fpcurthread = %p, curthread = %p, hw_float = %d\n", + PCPU_GET(fpcurthread), curthread, hw_float); panic("npxtrap from nowhere"); } savecrit = intr_disable(); @@ -748,7 +647,7 @@ npxdna(void) struct pcb *pcb; register_t s; - if (!npx_exists) + if (!hw_float) return (0); if (PCPU_GET(fpcurthread) == curthread) { printf("npxdna: fpcurthread == curthread %d times\n", @@ -879,7 +778,7 @@ npxgetregs(struct thread *td, union save struct pcb *pcb; register_t s; - if (!npx_exists) + if (!hw_float) return (_MC_FPOWNED_NONE); pcb = td->td_pcb; @@ -915,7 +814,7 @@ npxgetuserregs(struct thread *td, union struct pcb *pcb; register_t s; - if (!npx_exists) + if (!hw_float) return (_MC_FPOWNED_NONE); pcb = td->td_pcb; @@ -954,7 +853,7 @@ npxsetregs(struct thread *td, union save struct pcb *pcb; register_t s; - if (!npx_exists) + if (!hw_float) return; pcb = td->td_pcb; @@ -981,7 +880,7 @@ npxsetuserregs(struct thread *td, union struct pcb *pcb; register_t s; - if (!npx_exists) + if (!hw_float) return; pcb = td->td_pcb; Modified: head/sys/kern/subr_trap.c ============================================================================== --- head/sys/kern/subr_trap.c Wed Jun 23 10:40:28 2010 (r209460) +++ head/sys/kern/subr_trap.c Wed Jun 23 11:12:58 2010 (r209461) @@ -46,9 +46,6 @@ __FBSDID("$FreeBSD$"); #include "opt_ktrace.h" #include "opt_kdtrace.h" -#ifdef __i386__ -#include "opt_npx.h" -#endif #include "opt_sched.h" #include <sys/param.h> @@ -75,7 +72,6 @@ __FBSDID("$FreeBSD$"); #include <security/audit/audit.h> #include <machine/cpu.h> -#include <machine/pcb.h> #ifdef XEN #include <vm/vm.h> @@ -147,10 +143,6 @@ ast(struct trapframe *framep) struct proc *p; int flags; int sig; -#if defined(DEV_NPX) && !defined(SMP) - int ucode; - ksiginfo_t ksi; -#endif td = curthread; p = td->td_proc; @@ -190,19 +182,6 @@ ast(struct trapframe *framep) psignal(p, SIGVTALRM); PROC_UNLOCK(p); } -#if defined(DEV_NPX) && !defined(SMP) - if (PCPU_GET(curpcb)->pcb_flags & PCB_NPXTRAP) { - atomic_clear_int(&PCPU_GET(curpcb)->pcb_flags, - PCB_NPXTRAP); - ucode = npxtrap(); - if (ucode != -1) { - ksiginfo_init_trap(&ksi); - ksi.ksi_signo = SIGFPE; - ksi.ksi_code = ucode; - trapsignal(td, &ksi); - } - } -#endif if (flags & TDF_PROFPEND) { PROC_LOCK(p); psignal(p, SIGPROF); Modified: head/sys/pc98/include/npx.h ============================================================================== --- head/sys/pc98/include/npx.h Wed Jun 23 10:40:28 2010 (r209460) +++ head/sys/pc98/include/npx.h Wed Jun 23 11:12:58 2010 (r209461) @@ -1,49 +1,6 @@ /*- - * Copyright (C) 2005 TAKAHASHI Yoshihiro. 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 AUTHOR AND CONTRIBUTORS ``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 AUTHOR OR CONTRIBUTORS 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. - * - * $FreeBSD$ + * This file is in the public domain. */ - -#ifndef _PC98_INCLUDE_NPX_H_ -#define _PC98_INCLUDE_NPX_H_ +/* $FreeBSD$ */ #include <i386/npx.h> - -#ifdef _KERNEL - -#undef IO_NPX -#define IO_NPX 0x0F8 /* Numeric Coprocessor */ -#undef IO_NPXSIZE -#define IO_NPXSIZE 8 /* 80387/80487 NPX registers */ - -#undef IRQ_NPX -#define IRQ_NPX 8 - -/* full reset of npx: not needed on pc98 */ -#undef npx_full_reset -#define npx_full_reset() - -#endif /* _KERNEL */ - -#endif /* _PC98_INCLUDE_NPX_H_ */
Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?201006231112.o5NBCxml047925>