[BACK]Return to x_ovfl.sa CVS log [TXT][DIR] Up to [local] / sys / arch / m68k / fpsp

File: [local] / sys / arch / m68k / fpsp / x_ovfl.sa (download)

Revision 1.1, Tue Mar 4 16:07:08 2008 UTC (16 years, 2 months ago) by nbrk
Branch point for: MAIN

Initial revision

*	$OpenBSD: x_ovfl.sa,v 1.3 2001/09/20 17:02:30 mpech Exp $
*	$NetBSD: x_ovfl.sa,v 1.2 1994/10/26 07:50:26 cgd Exp $

*	MOTOROLA MICROPROCESSOR & MEMORY TECHNOLOGY GROUP
*	M68000 Hi-Performance Microprocessor Division
*	M68040 Software Package 
*
*	M68040 Software Package Copyright (c) 1993, 1994 Motorola Inc.
*	All rights reserved.
*
*	THE SOFTWARE is provided on an "AS IS" basis and without warranty.
*	To the maximum extent permitted by applicable law,
*	MOTOROLA DISCLAIMS ALL WARRANTIES WHETHER EXPRESS OR IMPLIED,
*	INCLUDING IMPLIED WARRANTIES OF MERCHANTABILITY OR FITNESS FOR A
*	PARTICULAR PURPOSE and any warranty against infringement with
*	regard to the SOFTWARE (INCLUDING ANY MODIFIED VERSIONS THEREOF)
*	and any accompanying written materials. 
*
*	To the maximum extent permitted by applicable law,
*	IN NO EVENT SHALL MOTOROLA BE LIABLE FOR ANY DAMAGES WHATSOEVER
*	(INCLUDING WITHOUT LIMITATION, DAMAGES FOR LOSS OF BUSINESS
*	PROFITS, BUSINESS INTERRUPTION, LOSS OF BUSINESS INFORMATION, OR
*	OTHER PECUNIARY LOSS) ARISING OF THE USE OR INABILITY TO USE THE
*	SOFTWARE.  Motorola assumes no responsibility for the maintenance
*	and support of the SOFTWARE.  
*
*	You are hereby granted a copyright license to use, modify, and
*	distribute the SOFTWARE so long as this entire notice is retained
*	without alteration in any modified and/or redistributed versions,
*	and that such modified versions are clearly identified as such.
*	No licenses are granted by implication, estoppel or otherwise
*	under any patents or trademarks of Motorola, Inc.

*
*	x_ovfl.sa 3.5 7/1/91
*
*	fpsp_ovfl --- FPSP handler for overflow exception
*
*	Overflow occurs when a floating-point intermediate result is
*	too large to be represented in a floating-point data register,
*	or when storing to memory, the contents of a floating-point
*	data register are too large to be represented in the
*	destination format.
*		
* Trap disabled results
*
* If the instruction is move_out, then garbage is stored in the
* destination.  If the instruction is not move_out, then the
* destination is not affected.  For 68881 compatibility, the
* following values should be stored at the destination, based
* on the current rounding mode:
*
*  RN	Infinity with the sign of the intermediate result.
*  RZ	Largest magnitude number, with the sign of the
*	intermediate result.
*  RM   For pos overflow, the largest pos number. For neg overflow,
*	-infinity
*  RP   For pos overflow, +infinity. For neg overflow, the largest
*	neg number
*
* Trap enabled results
* All trap disabled code applies.  In addition the exceptional
* operand needs to be made available to the users exception handler
* with a bias of $6000 subtracted from the exponent.
*

X_OVFL	IDNT    2,1 Motorola 040 Floating Point Software Package

	section	8

	include	fpsp.h

	xref	ovf_r_x2
	xref	ovf_r_x3
	xref	store
	xref	real_ovfl
	xref	real_inex
	xref	fpsp_done
	xref	g_opcls
	xref	b1238_fix

	xdef	fpsp_ovfl
fpsp_ovfl:
	link		a6,#-LOCAL_SIZE
	fsave		-(a7)
	movem.l		d0-d1/a0-a1,USER_DA(a6)
	fmovem.x	fp0-fp3,USER_FP0(a6)
	fmovem.l	fpcr/fpsr/fpiar,USER_FPCR(a6)

*
*	The 040 doesn't set the AINEX bit in the FPSR, the following
*	line temporarily rectifies this error.
*
	bset.b	#ainex_bit,FPSR_AEXCEPT(a6)
*
	bsr.l	ovf_adj		;denormalize, round & store interm op
*
*	if overflow traps not enabled check for inexact exception
*
	btst.b	#ovfl_bit,FPCR_ENABLE(a6)
	beq.b	ck_inex	
*
	btst.b		#E3,E_BYTE(a6)
	beq.b		no_e3_1
	bfextu		CMDREG3B(a6){6:3},d0	;get dest reg no
	bclr.b		d0,FPR_DIRTY_BITS(a6)	;clr dest dirty bit
	bsr.l		b1238_fix
	move.l		USER_FPSR(a6),FPSR_SHADOW(a6)
	or.l		#sx_mask,E_BYTE(a6)
no_e3_1:
	movem.l		USER_DA(a6),d0-d1/a0-a1
	fmovem.x	USER_FP0(a6),fp0-fp3
	fmovem.l	USER_FPCR(a6),fpcr/fpsr/fpiar
	frestore	(a7)+
	unlk		a6
	bra.l		real_ovfl
*
* It is possible to have either inex2 or inex1 exceptions with the
* ovfl.  If the inex enable bit is set in the FPCR, and either
* inex2 or inex1 occurred, we must clean up and branch to the
* real inex handler.
*
ck_inex:
*	move.b		FPCR_ENABLE(a6),d0
*	and.b		FPSR_EXCEPT(a6),d0
*	andi.b		#$3,d0
	btst.b		#inex2_bit,FPCR_ENABLE(a6)
	beq.b		ovfl_exit
*
* Inexact enabled and reported, and we must take an inexact exception.
*
take_inex:
	btst.b		#E3,E_BYTE(a6)
	beq.b		no_e3_2
	bfextu		CMDREG3B(a6){6:3},d0	;get dest reg no
	bclr.b		d0,FPR_DIRTY_BITS(a6)	;clr dest dirty bit
	bsr.l		b1238_fix
	move.l		USER_FPSR(a6),FPSR_SHADOW(a6)
	or.l		#sx_mask,E_BYTE(a6)
no_e3_2:
	move.b		#INEX_VEC,EXC_VEC+1(a6)
	movem.l		USER_DA(a6),d0-d1/a0-a1
	fmovem.x	USER_FP0(a6),fp0-fp3
	fmovem.l	USER_FPCR(a6),fpcr/fpsr/fpiar
	frestore	(a7)+
	unlk		a6
	bra.l		real_inex
	
ovfl_exit:
	bclr.b	#E3,E_BYTE(a6)	;test and clear E3 bit
	beq.b	e1_set
*
* Clear dirty bit on dest resister in the frame before branching
* to b1238_fix.
*
	bfextu		CMDREG3B(a6){6:3},d0	;get dest reg no
	bclr.b		d0,FPR_DIRTY_BITS(a6)	;clr dest dirty bit
	bsr.l		b1238_fix		;test for bug1238 case

	move.l		USER_FPSR(a6),FPSR_SHADOW(a6)
	or.l		#sx_mask,E_BYTE(a6)
	movem.l		USER_DA(a6),d0-d1/a0-a1
	fmovem.x	USER_FP0(a6),fp0-fp3
	fmovem.l	USER_FPCR(a6),fpcr/fpsr/fpiar
	frestore	(a7)+
	unlk		a6
	bra.l		fpsp_done
e1_set:
	movem.l		USER_DA(a6),d0-d1/a0-a1
	fmovem.x	USER_FP0(a6),fp0-fp3
	fmovem.l	USER_FPCR(a6),fpcr/fpsr/fpiar
	unlk		a6
	bra.l		fpsp_done

*
*	ovf_adj
*
ovf_adj:
*
* Have a0 point to the correct operand. 
*
	btst.b	#E3,E_BYTE(a6)	;test E3 bit
	beq.b	ovf_e1

	lea	WBTEMP(a6),a0
	bra.b	ovf_com
ovf_e1:
	lea	ETEMP(a6),a0

ovf_com:
	bclr.b	#sign_bit,LOCAL_EX(a0)
	sne	LOCAL_SGN(a0)

	bsr.l	g_opcls		;returns opclass in d0
	cmpi.w	#3,d0		;check for opclass3
	bne.b	not_opc011

*
* FPSR_CC is saved and restored because ovf_r_x3 affects it. The
* CCs are defined to be 'not affected' for the opclass3 instruction.
*
	move.b	FPSR_CC(a6),L_SCR1(a6)
 	bsr.l	ovf_r_x3	;returns a0 pointing to result
	move.b	L_SCR1(a6),FPSR_CC(a6)
	bra.l	store		;stores to memory or register
	
not_opc011:
	bsr.l	ovf_r_x2	;returns a0 pointing to result
	bra.l	store		;stores to memory or register

	end