cachepc-linux

Fork of AMDESE/linux with modifications for CachePC side-channel attack
git clone https://git.sinitax.com/sinitax/cachepc-linux
Log | Files | Refs | README | LICENSE | sfeed.txt

x_ovfl.S (4743B)


      1|
      2|	x_ovfl.sa 3.5 7/1/91
      3|
      4|	fpsp_ovfl --- FPSP handler for overflow exception
      5|
      6|	Overflow occurs when a floating-point intermediate result is
      7|	too large to be represented in a floating-point data register,
      8|	or when storing to memory, the contents of a floating-point
      9|	data register are too large to be represented in the
     10|	destination format.
     11|
     12| Trap disabled results
     13|
     14| If the instruction is move_out, then garbage is stored in the
     15| destination.  If the instruction is not move_out, then the
     16| destination is not affected.  For 68881 compatibility, the
     17| following values should be stored at the destination, based
     18| on the current rounding mode:
     19|
     20|  RN	Infinity with the sign of the intermediate result.
     21|  RZ	Largest magnitude number, with the sign of the
     22|	intermediate result.
     23|  RM   For pos overflow, the largest pos number. For neg overflow,
     24|	-infinity
     25|  RP   For pos overflow, +infinity. For neg overflow, the largest
     26|	neg number
     27|
     28| Trap enabled results
     29| All trap disabled code applies.  In addition the exceptional
     30| operand needs to be made available to the users exception handler
     31| with a bias of $6000 subtracted from the exponent.
     32|
     33|
     34
     35|		Copyright (C) Motorola, Inc. 1990
     36|			All Rights Reserved
     37|
     38|       For details on the license for this file, please see the
     39|       file, README, in this same directory.
     40
     41X_OVFL:	|idnt    2,1 | Motorola 040 Floating Point Software Package
     42
     43	|section	8
     44
     45#include "fpsp.h"
     46
     47	|xref	ovf_r_x2
     48	|xref	ovf_r_x3
     49	|xref	store
     50	|xref	real_ovfl
     51	|xref	real_inex
     52	|xref	fpsp_done
     53	|xref	g_opcls
     54	|xref	b1238_fix
     55
     56	.global	fpsp_ovfl
     57fpsp_ovfl:
     58	link		%a6,#-LOCAL_SIZE
     59	fsave		-(%a7)
     60	moveml		%d0-%d1/%a0-%a1,USER_DA(%a6)
     61	fmovemx	%fp0-%fp3,USER_FP0(%a6)
     62	fmoveml	%fpcr/%fpsr/%fpiar,USER_FPCR(%a6)
     63
     64|
     65|	The 040 doesn't set the AINEX bit in the FPSR, the following
     66|	line temporarily rectifies this error.
     67|
     68	bsetb	#ainex_bit,FPSR_AEXCEPT(%a6)
     69|
     70	bsrl	ovf_adj		|denormalize, round & store interm op
     71|
     72|	if overflow traps not enabled check for inexact exception
     73|
     74	btstb	#ovfl_bit,FPCR_ENABLE(%a6)
     75	beqs	ck_inex
     76|
     77	btstb		#E3,E_BYTE(%a6)
     78	beqs		no_e3_1
     79	bfextu		CMDREG3B(%a6){#6:#3},%d0	|get dest reg no
     80	bclrb		%d0,FPR_DIRTY_BITS(%a6)	|clr dest dirty bit
     81	bsrl		b1238_fix
     82	movel		USER_FPSR(%a6),FPSR_SHADOW(%a6)
     83	orl		#sx_mask,E_BYTE(%a6)
     84no_e3_1:
     85	moveml		USER_DA(%a6),%d0-%d1/%a0-%a1
     86	fmovemx	USER_FP0(%a6),%fp0-%fp3
     87	fmoveml	USER_FPCR(%a6),%fpcr/%fpsr/%fpiar
     88	frestore	(%a7)+
     89	unlk		%a6
     90	bral		real_ovfl
     91|
     92| It is possible to have either inex2 or inex1 exceptions with the
     93| ovfl.  If the inex enable bit is set in the FPCR, and either
     94| inex2 or inex1 occurred, we must clean up and branch to the
     95| real inex handler.
     96|
     97ck_inex:
     98|	move.b		FPCR_ENABLE(%a6),%d0
     99|	and.b		FPSR_EXCEPT(%a6),%d0
    100|	andi.b		#$3,%d0
    101	btstb		#inex2_bit,FPCR_ENABLE(%a6)
    102	beqs		ovfl_exit
    103|
    104| Inexact enabled and reported, and we must take an inexact exception.
    105|
    106take_inex:
    107	btstb		#E3,E_BYTE(%a6)
    108	beqs		no_e3_2
    109	bfextu		CMDREG3B(%a6){#6:#3},%d0	|get dest reg no
    110	bclrb		%d0,FPR_DIRTY_BITS(%a6)	|clr dest dirty bit
    111	bsrl		b1238_fix
    112	movel		USER_FPSR(%a6),FPSR_SHADOW(%a6)
    113	orl		#sx_mask,E_BYTE(%a6)
    114no_e3_2:
    115	moveb		#INEX_VEC,EXC_VEC+1(%a6)
    116	moveml		USER_DA(%a6),%d0-%d1/%a0-%a1
    117	fmovemx	USER_FP0(%a6),%fp0-%fp3
    118	fmoveml	USER_FPCR(%a6),%fpcr/%fpsr/%fpiar
    119	frestore	(%a7)+
    120	unlk		%a6
    121	bral		real_inex
    122
    123ovfl_exit:
    124	bclrb	#E3,E_BYTE(%a6)	|test and clear E3 bit
    125	beqs	e1_set
    126|
    127| Clear dirty bit on dest resister in the frame before branching
    128| to b1238_fix.
    129|
    130	bfextu		CMDREG3B(%a6){#6:#3},%d0	|get dest reg no
    131	bclrb		%d0,FPR_DIRTY_BITS(%a6)	|clr dest dirty bit
    132	bsrl		b1238_fix		|test for bug1238 case
    133
    134	movel		USER_FPSR(%a6),FPSR_SHADOW(%a6)
    135	orl		#sx_mask,E_BYTE(%a6)
    136	moveml		USER_DA(%a6),%d0-%d1/%a0-%a1
    137	fmovemx	USER_FP0(%a6),%fp0-%fp3
    138	fmoveml	USER_FPCR(%a6),%fpcr/%fpsr/%fpiar
    139	frestore	(%a7)+
    140	unlk		%a6
    141	bral		fpsp_done
    142e1_set:
    143	moveml		USER_DA(%a6),%d0-%d1/%a0-%a1
    144	fmovemx	USER_FP0(%a6),%fp0-%fp3
    145	fmoveml	USER_FPCR(%a6),%fpcr/%fpsr/%fpiar
    146	unlk		%a6
    147	bral		fpsp_done
    148
    149|
    150|	ovf_adj
    151|
    152ovf_adj:
    153|
    154| Have a0 point to the correct operand.
    155|
    156	btstb	#E3,E_BYTE(%a6)	|test E3 bit
    157	beqs	ovf_e1
    158
    159	lea	WBTEMP(%a6),%a0
    160	bras	ovf_com
    161ovf_e1:
    162	lea	ETEMP(%a6),%a0
    163
    164ovf_com:
    165	bclrb	#sign_bit,LOCAL_EX(%a0)
    166	sne	LOCAL_SGN(%a0)
    167
    168	bsrl	g_opcls		|returns opclass in d0
    169	cmpiw	#3,%d0		|check for opclass3
    170	bnes	not_opc011
    171
    172|
    173| FPSR_CC is saved and restored because ovf_r_x3 affects it. The
    174| CCs are defined to be 'not affected' for the opclass3 instruction.
    175|
    176	moveb	FPSR_CC(%a6),L_SCR1(%a6)
    177	bsrl	ovf_r_x3	|returns a0 pointing to result
    178	moveb	L_SCR1(%a6),FPSR_CC(%a6)
    179	bral	store		|stores to memory or register
    180
    181not_opc011:
    182	bsrl	ovf_r_x2	|returns a0 pointing to result
    183	bral	store		|stores to memory or register
    184
    185	|end