Module Name: src Committed By: snj Date: Tue Jan 3 06:19:21 UTC 2017
Modified Files: src/sys/arch/powerpc/fpu [netbsd-7]: fpu_emu.c fpu_explode.c Log Message: Pull up following revision(s) (requested by rin in ticket #1341): sys/arch/powerpc/fpu/fpu_emu.c: revision 1.19 sys/arch/powerpc/fpu/fpu_explode.c: revision 1.7 - add missing default from FreeBSD - remove duplicate panic pointed out by matt -- PR port-powerpc/51368: powerpc FPU emulation fails for single precision floating point arithmetic For single precision instruction, calculate first in double precision, and then round it. With this fix, single precision arithmetic gets sane on ibm4xx and booke. Taken from FreeBSD commit r258250: https://svnweb.freebsd.org/base?view=revision&revision=258250 Ok matt and simonb. To generate a diff of this commit: cvs rdiff -u -r1.16 -r1.16.14.1 src/sys/arch/powerpc/fpu/fpu_emu.c cvs rdiff -u -r1.6 -r1.6.140.1 src/sys/arch/powerpc/fpu/fpu_explode.c Please note that diffs are not public domain; they are subject to the copyright notices on the relevant files.
Modified files: Index: src/sys/arch/powerpc/fpu/fpu_emu.c diff -u src/sys/arch/powerpc/fpu/fpu_emu.c:1.16 src/sys/arch/powerpc/fpu/fpu_emu.c:1.16.14.1 --- src/sys/arch/powerpc/fpu/fpu_emu.c:1.16 Mon Jul 23 04:13:06 2012 +++ src/sys/arch/powerpc/fpu/fpu_emu.c Tue Jan 3 06:19:21 2017 @@ -1,4 +1,4 @@ -/* $NetBSD: fpu_emu.c,v 1.16 2012/07/23 04:13:06 matt Exp $ */ +/* $NetBSD: fpu_emu.c,v 1.16.14.1 2017/01/03 06:19:21 snj Exp $ */ /* * Copyright 2001 Wasabi Systems, Inc. @@ -76,7 +76,7 @@ */ #include <sys/cdefs.h> -__KERNEL_RCSID(0, "$NetBSD: fpu_emu.c,v 1.16 2012/07/23 04:13:06 matt Exp $"); +__KERNEL_RCSID(0, "$NetBSD: fpu_emu.c,v 1.16.14.1 2017/01/03 06:19:21 snj Exp $"); #include "opt_ddb.h" @@ -626,9 +626,11 @@ fpu_execute(struct trapframe *tf, struct rb = instr.i_a.i_frb; rc = instr.i_a.i_frc; - type = FTYPE_SNG; - if (instr.i_any.i_opcd & 0x4) - type = FTYPE_DBL; + /* + * All arithmetic operations work on registers, which + * are stored as doubles. + */ + type = FTYPE_DBL; switch ((unsigned int)instr.i_a.i_xo) { case OPC59_FDIVS: FPU_EMU_EVCNT_INCR(fdiv); @@ -745,6 +747,13 @@ fpu_execute(struct trapframe *tf, struct return (NOTFPU); break; } + + /* If the instruction was single precision, round */ + if (!(instr.i_any.i_opcd & 0x4)) { + fpu_implode(fe, fp, FTYPE_SNG, + (u_int *)&fs->fpreg[rt]); + fpu_explode(fe, fp = &fe->fe_f1, FTYPE_SNG, rt); + } } } else { return (NOTFPU); Index: src/sys/arch/powerpc/fpu/fpu_explode.c diff -u src/sys/arch/powerpc/fpu/fpu_explode.c:1.6 src/sys/arch/powerpc/fpu/fpu_explode.c:1.6.140.1 --- src/sys/arch/powerpc/fpu/fpu_explode.c:1.6 Sun Dec 11 12:18:42 2005 +++ src/sys/arch/powerpc/fpu/fpu_explode.c Tue Jan 3 06:19:21 2017 @@ -1,4 +1,4 @@ -/* $NetBSD: fpu_explode.c,v 1.6 2005/12/11 12:18:42 christos Exp $ */ +/* $NetBSD: fpu_explode.c,v 1.6.140.1 2017/01/03 06:19:21 snj Exp $ */ /* * Copyright (c) 1992, 1993 @@ -46,7 +46,7 @@ */ #include <sys/cdefs.h> -__KERNEL_RCSID(0, "$NetBSD: fpu_explode.c,v 1.6 2005/12/11 12:18:42 christos Exp $"); +__KERNEL_RCSID(0, "$NetBSD: fpu_explode.c,v 1.6.140.1 2017/01/03 06:19:21 snj Exp $"); #include <sys/types.h> #include <sys/systm.h> @@ -235,7 +235,7 @@ fpu_explode(struct fpemu *fe, struct fpn s = fpu_dtof(fp, s, space[1]); break; - panic("fpu_explode"); + default: panic("fpu_explode: invalid type %d", type); }