2005-04-16 15:20:36 -07:00
|
| x_ o p e r r . s a 3 . 5 7 / 1 / 9 1
|
| fpsp_ o p e r r - - - F P S P h a n d l e r f o r o p e r a n d e r r o r e x c e p t i o n
|
| See 6 8 0 4 0 U s e r ' s M a n u a l p p . 9 - 4 4 f
|
| Note 1 : F o r t r a p d i s a b l e d 0 4 0 d o e s t h e f o l l o w i n g :
| If t h e d e s t i s a f p r e g , t h e n a n e x t e n d e d p r e c i s i o n n o n _ s i g n a l i n g
| NAN i s s t o r e d i n t h e d e s t r e g . I f t h e d e s t f o r m a t i s b , w , o r l a n d
| the s o u r c e o p i s a N A N , t h e n g a r b a g e i s s t o r e d a s t h e r e s u l t ( a c t u a l l y
| the u p p e r 3 2 b i t s o f t h e m a n t i s s a a r e s e n t t o t h e i n t e g e r u n i t ) . I f
| the d e s t f o r m a t i s i n t e g e r ( b , w , l ) a n d t h e o p e r r i s c a u s e d b y
| integer o v e r f l o w , o r t h e s o u r c e o p i s i n f , t h e n t h e r e s u l t s t o r e d i s
| garbage.
| There a r e t h r e e c a s e s i n w h i c h o p e r r i s i n c o r r e c t l y s i g n a l e d o n t h e
| 0 4 0 . This o c c u r s f o r m o v e _ o u t o f f o r m a t b , w , o r l f o r t h e l a r g e s t
| negative i n t e g e r ( - 2 ^ 7 f o r b , - 2 ^ 1 5 f o r w , - 2 ^ 3 1 f o r l ) .
|
| On o p c l a s s = 0 1 1 f m o v e . ( b ,w ,l ) t h a t c a u s e s a c o n v e r s i o n
| overflow - > O P E R R , t h e e x p o n e n t i n w b t e ( a n d f p t e ) i s :
| byte 5 6 - ( 6 2 - e x p )
| word 4 8 - ( 6 2 - e x p )
| long 3 2 - ( 6 2 - e x p )
|
| where e x p = ( t r u e e x p ) - 1
|
| So, w b t e m p a n d f p t e m p w i l l c o n t a i n t h e f o l l o w i n g o n e r r o n e o u s l y
| signalled o p e r r :
| fpts = 1
| fpte = $ 4 0 0 0 ( 1 5 b i t e x t e r n a l l y )
| byte f p t m = $ f f f f f f f f f f f f f f80
| word f p t m = $ f f f f f f f f f f f f80 0 0
| long f p t m = $ f f f f f f f f 8 0 0 0 0 0 0 0
|
| Note 2 : F o r t r a p e n a b l e d 0 4 0 d o e s t h e f o l l o w i n g :
| If t h e i n s t i s m o v e _ o u t , t h e n s a m e a s N o t e 1 .
| If t h e i n s t i s n o t m o v e _ o u t , t h e d e s t i s n o t m o d i f i e d .
| The e x c e p t i o n a l o p e r a n d i s n o t d e f i n e d f o r i n t e g e r o v e r f l o w
| during a m o v e _ o u t .
|
| Copyright ( C ) M o t o r o l a , I n c . 1 9 9 0
| All R i g h t s R e s e r v e d
|
2006-02-11 17:55:48 -08:00
| For d e t a i l s o n t h e l i c e n s e f o r t h i s f i l e , p l e a s e s e e t h e
| file, R E A D M E , i n t h i s s a m e d i r e c t o r y .
2005-04-16 15:20:36 -07:00
X_OPERR : | idnt 2 ,1 | M o t o r o l a 0 4 0 F l o a t i n g P o i n t S o f t w a r e P a c k a g e
| section 8
# include " f p s p . h "
| xref m e m _ w r i t e
| xref r e a l _ o p e r r
| xref r e a l _ i n e x
| xref g e t _ f l i n e
| xref f p s p _ d o n e
| xref r e g _ d e s t
.global fpsp_operr
fpsp_operr :
|
link % a6 ,#- L O C A L _ S I Z E
fsave - ( % a7 )
moveml % d0 - % d1 / % a0 - % a1 ,U S E R _ D A ( % a6 )
fmovemx % f p0 - % f p3 ,U S E R _ F P 0 ( % a6 )
fmoveml % f p c r / % f p s r / % f p i a r ,U S E R _ F P C R ( % a6 )
|
| Check i f t h i s i s a n o p c l a s s 3 i n s t r u c t i o n .
| If s o , f a l l t h r o u g h , e l s e b r a n c h t o o p e r r _ e n d
|
btstb #T F L A G , T _ B Y T E ( % a 6 )
beqs o p e r r _ e n d
|
| If t h e d e s t i n a t i o n s i z e i s B ,W ,o r L , t h e o p e r r m u s t b e
| handled h e r e .
|
movel C M D R E G 1 B ( % a6 ) ,% d0
bfextu % d0 { #3 : #3 } ,% d0 | 0 =long , 4 =word , 6 =byte
cmpib #0 ,% d0 | d e t e r m i n e s i z e ; check long
beq o p e r r _ l o n g
cmpib #4 ,% d0 | c h e c k w o r d
beq o p e r r _ w o r d
cmpib #6 ,% d0 | c h e c k b y t e
beq o p e r r _ b y t e
|
| The s i z e i s n o t B ,W ,o r L , s o t h e o p e r r i s h a n d l e d b y t h e
| kernel h a n d l e r . S e t t h e o p e r r b i t s a n d c l e a n u p , l e a v i n g
| only t h e i n t e g e r e x c e p t i o n f r a m e o n t h e s t a c k , a n d t h e
| fpu i n t h e o r i g i n a l e x c e p t i o n a l s t a t e .
|
operr_end :
bsetb #o p e r r _ b i t , F P S R _ E X C E P T ( % a 6 )
bsetb #a i o p _ b i t , F P S R _ A E X C E P T ( % a 6 )
moveml U S E R _ D A ( % a6 ) ,% d0 - % d1 / % a0 - % a1
fmovemx U S E R _ F P 0 ( % a6 ) ,% f p0 - % f p3
fmoveml U S E R _ F P C R ( % a6 ) ,% f p c r / % f p s r / % f p i a r
frestore ( % a7 ) +
unlk % a6
bral r e a l _ o p e r r
operr_long :
moveql #4 ,% d1 | w r i t e s i z e t o d1
moveb S T A G ( % a6 ) ,% d0 | t e s t s t a g f o r n a n
andib #0xe0 ,% d0 | c l r a l l b u t t a g
cmpib #0x60 ,% d0 | c h e c k f o r n a n
beq o p e r r _ n a n
cmpil #0x80000000 ,F P T E M P _ L O ( % a6 ) | t e s t i f l s l w o r d i s s p e c i a l
bnes c h k l e r r | i f n o t e q u a l , c h e c k f o r i n c o r r e c t o p e r r
bsr c h e c k _ u p p e r | c h e c k i f e x p a n d m s m a n t a r e s p e c i a l
tstl % d0
bnes c h k l e r r | i f d0 i s t r u e , c h e c k f o r i n c o r r e c t o p e r r
movel #0x80000000 ,% d0 | s t o r e s p e c i a l c a s e r e s u l t
bsr o p e r r _ s t o r e
bra n o t _ e n a b l e d | c l e a n a n d e x i t
|
| CHECK F O R I N C O R R E C T L Y G E N E R A T E D O P E R R E X C E P T I O N H E R E
|
chklerr :
movew F P T E M P _ E X ( % a6 ) ,% d0
andw #0x7FFF ,% d0 | i g n o r e s i g n b i t
cmpw #0x3FFE ,% d0 | t h i s i s t h e o n l y p o s s i b l e e x p o n e n t v a l u e
bnes c h k l e r r2
fixlong :
movel F P T E M P _ L O ( % a6 ) ,% d0
bsr o p e r r _ s t o r e
bra n o t _ e n a b l e d
chklerr2 :
movew F P T E M P _ E X ( % a6 ) ,% d0
andw #0x7FFF ,% d0 | i g n o r e s i g n b i t
cmpw #0x4000 ,% d0
bcc s t o r e _ m a x | e x p o n e n t o u t o f r a n g e
movel F P T E M P _ L O ( % a6 ) ,% d0
andl #0x7FFF0000 ,% d0 | l o o k f o r a l l 1 ' s o n b i t s 3 0 - 1 6
cmpl #0x7FFF0000 ,% d0
beqs f i x l o n g
tstl F P T E M P _ L O ( % a6 )
bpls c h k l e p o s
cmpl #0xFFFFFFFF ,F P T E M P _ H I ( % a6 )
beqs f i x l o n g
bra s t o r e _ m a x
chklepos :
tstl F P T E M P _ H I ( % a6 )
beqs f i x l o n g
bra s t o r e _ m a x
operr_word :
moveql #2 ,% d1 | w r i t e s i z e t o d1
moveb S T A G ( % a6 ) ,% d0 | t e s t s t a g f o r n a n
andib #0xe0 ,% d0 | c l r a l l b u t t a g
cmpib #0x60 ,% d0 | c h e c k f o r n a n
beq o p e r r _ n a n
cmpil #0xffff8000 ,F P T E M P _ L O ( % a6 ) | t e s t i f l s l w o r d i s s p e c i a l
bnes c h k w e r r | i f n o t e q u a l , c h e c k f o r i n c o r r e c t o p e r r
bsr c h e c k _ u p p e r | c h e c k i f e x p a n d m s m a n t a r e s p e c i a l
tstl % d0
bnes c h k w e r r | i f d0 i s t r u e , c h e c k f o r i n c o r r e c t o p e r r
movel #0x80000000 ,% d0 | s t o r e s p e c i a l c a s e r e s u l t
bsr o p e r r _ s t o r e
bra n o t _ e n a b l e d | c l e a n a n d e x i t
|
| CHECK F O R I N C O R R E C T L Y G E N E R A T E D O P E R R E X C E P T I O N H E R E
|
chkwerr :
movew F P T E M P _ E X ( % a6 ) ,% d0
andw #0x7FFF ,% d0 | i g n o r e s i g n b i t
cmpw #0x3FFE ,% d0 | t h i s i s t h e o n l y p o s s i b l e e x p o n e n t v a l u e
bnes s t o r e _ m a x
movel F P T E M P _ L O ( % a6 ) ,% d0
swap % d0
bsr o p e r r _ s t o r e
bra n o t _ e n a b l e d
operr_byte :
moveql #1 ,% d1 | w r i t e s i z e t o d1
moveb S T A G ( % a6 ) ,% d0 | t e s t s t a g f o r n a n
andib #0xe0 ,% d0 | c l r a l l b u t t a g
cmpib #0x60 ,% d0 | c h e c k f o r n a n
beqs o p e r r _ n a n
cmpil #0xffffff80 ,F P T E M P _ L O ( % a6 ) | t e s t i f l s l w o r d i s s p e c i a l
bnes c h k b e r r | i f n o t e q u a l , c h e c k f o r i n c o r r e c t o p e r r
bsr c h e c k _ u p p e r | c h e c k i f e x p a n d m s m a n t a r e s p e c i a l
tstl % d0
bnes c h k b e r r | i f d0 i s t r u e , c h e c k f o r i n c o r r e c t o p e r r
movel #0x80000000 ,% d0 | s t o r e s p e c i a l c a s e r e s u l t
bsr o p e r r _ s t o r e
bra n o t _ e n a b l e d | c l e a n a n d e x i t
|
| CHECK F O R I N C O R R E C T L Y G E N E R A T E D O P E R R E X C E P T I O N H E R E
|
chkberr :
movew F P T E M P _ E X ( % a6 ) ,% d0
andw #0x7FFF ,% d0 | i g n o r e s i g n b i t
cmpw #0x3FFE ,% d0 | t h i s i s t h e o n l y p o s s i b l e e x p o n e n t v a l u e
bnes s t o r e _ m a x
movel F P T E M P _ L O ( % a6 ) ,% d0
asll #8 ,% d0
swap % d0
bsr o p e r r _ s t o r e
bra n o t _ e n a b l e d
|
| This o p e r r c o n d i t i o n i s n o t o f t h e s p e c i a l c a s e . S e t o p e r r
| and a i o p a n d w r i t e t h e p o r t i o n o f t h e n a n t o m e m o r y f o r t h e
| given s i z e .
|
operr_nan :
orl #o p a o p _ m a s k , U S E R _ F P S R ( % a 6 ) | s e t o p e r r & a i o p
movel E T E M P _ H I ( % a6 ) ,% d0 | o u t p u t w i l l b e f r o m u p p e r 3 2 b i t s
bsr o p e r r _ s t o r e
bra e n d _ o p e r r
|
| Store_ m a x l o a d s t h e m a x p o s o r n e g a t i v e f o r t h e s i z e , s e t s
| the o p e r r a n d a i o p b i t s , a n d c l e a r s i n e x a n d a i n e x , i n c o r r e c t l y
| set b y t h e 0 4 0 .
|
store_max :
orl #o p a o p _ m a s k , U S E R _ F P S R ( % a 6 ) | s e t o p e r r & a i o p
bclrb #i n e x 2 _ b i t ,F P S R _ E X C E P T ( % a6 )
bclrb #a i n e x _ b i t , F P S R _ A E X C E P T ( % a 6 )
fmovel #0 ,% F P S R
tstw F P T E M P _ E X ( % a6 ) | c h e c k s i g n
blts l o a d _ n e g
movel #0x7fffffff ,% d0
bsr o p e r r _ s t o r e
bra e n d _ o p e r r
load_neg :
movel #0x80000000 ,% d0
bsr o p e r r _ s t o r e
bra e n d _ o p e r r
|
| This r o u t i n e s t o r e s t h e d a t a i n d0 , f o r t h e g i v e n s i z e i n d1 ,
| to m e m o r y o r d a t a r e g i s t e r a s r e q u i r e d . A r e a d o f t h e f l i n e
| is r e q u i r e d t o d e t e r m i n e t h e d e s t i n a t i o n .
|
operr_store :
movel % d0 ,L _ S C R 1 ( % a6 ) | m o v e w r i t e d a t a t o L _ S C R 1
movel % d1 ,- ( % a7 ) | s a v e r e g i s t e r s i z e
bsrl g e t _ f l i n e | f l i n e r e t u r n e d i n d0
movel ( % a7 ) + ,% d1
bftst % d0 { #26 : #3 } | i f m o d e i s z e r o , d e s t i s D n
bnes d e s t _ m e m
|
| Destination i s D n . G e t r e g i s t e r n u m b e r f r o m d0 . D a t a i s o n
| the s t a c k a t ( a7 ) . D 1 h a s s i z e : 1 =byte ,2 =word ,4 =long / s i n g l e
|
andil #7 ,% d0 | i s o l a t e r e g i s t e r n u m b e r
cmpil #4 ,% d1
beqs o p _ l o n g | t h e m o s t f r e q u e n t c a s e
cmpil #2 ,% d1
bnes o p _ c o n
orl #8 ,% d0
bras o p _ c o n
op_long :
orl #0x10 ,% d0
op_con :
movel % d0 ,% d1 | f o r m a t s i z e : r e g f o r r e g _ d e s t
bral r e g _ d e s t | c a l l t o r e g _ d e s t r e t u r n s t o c a l l e r
| ;of operr_store
|
| Destination i s m e m o r y . G e t < e a > f r o m i n t e g e r e x c e p t i o n f r a m e
| and c a l l m e m _ w r i t e .
|
dest_mem :
leal L _ S C R 1 ( % a6 ) ,% a0 | p u t p t r t o w r i t e d a t a i n a0
movel E X C _ E A ( % a6 ) ,% a1 | p u t u s e r d e s t i n a t i o n a d d r e s s i n a1
movel % d1 ,% d0 | p u t s i z e i n d0
bsrl m e m _ w r i t e
rts
|
| Check t h e e x p o n e n t f o r $ c00 0 a n d t h e u p p e r 3 2 b i t s o f t h e
| mantissa f o r $ f f f f f f f f . I f b o t h a r e t r u e , r e t u r n d0 c l r
| and s t o r e t h e l o w e r n b i t s o f t h e l e a s t l w o r d o f F P T E M P
| to d0 f o r w r i t e o u t . I f n o t , i t i s a r e a l o p e r r , a n d s e t d0 .
|
check_upper :
cmpil #0xffffffff ,F P T E M P _ H I ( % a6 ) | c h e c k i f f i r s t b y t e i s a l l 1 ' s
bnes t r u e _ o p e r r | i f n o t a l l 1 ' s t h e n w a s t r u e o p e r r
cmpiw #0xc000 ,F P T E M P _ E X ( % a6 ) | c h e c k i f i n c o r r e c t l y s i g n a l l e d
beqs n o t _ t r u e _ o p e r r | b r a n c h i f n o t t r u e o p e r r
cmpiw #0xbfff ,F P T E M P _ E X ( % a6 ) | c h e c k i f i n c o r r e c t l y s i g n a l l e d
beqs n o t _ t r u e _ o p e r r | b r a n c h i f n o t t r u e o p e r r
true_operr :
movel #1 ,% d0 | s i g n a l r e a l o p e r r
rts
not_true_operr :
clrl % d0 | s i g n a l n o r e a l o p e r r
rts
|
| End_ o p e r r t e s t s f o r o p e r r e n a b l e d . I f n o t , i t c l e a n s u p t h e s t a c k
| and d o e s a n r t e . I f e n a b l e d , i t c l e a n s u p t h e s t a c k a n d b r a n c h e s
| to t h e k e r n e l o p e r r h a n d l e r w i t h o n l y t h e i n t e g e r e x c e p t i o n
| frame o n t h e s t a c k a n d t h e f p u i n t h e o r i g i n a l e x c e p t i o n a l s t a t e
| with c o r r e c t d a t a w r i t t e n t o t h e d e s t i n a t i o n .
|
end_operr :
btstb #o p e r r _ b i t , F P C R _ E N A B L E ( % a 6 )
beqs n o t _ e n a b l e d
enabled :
moveml U S E R _ D A ( % a6 ) ,% d0 - % d1 / % a0 - % a1
fmovemx U S E R _ F P 0 ( % a6 ) ,% f p0 - % f p3
fmoveml U S E R _ F P C R ( % a6 ) ,% f p c r / % f p s r / % f p i a r
frestore ( % a7 ) +
unlk % a6
bral r e a l _ o p e r r
not_enabled :
|
| It i s p o s s i b l e t o h a v e e i t h e r i n e x2 o r i n e x1 e x c e p t i o n s w i t h t h e
| operr. I f t h e i n e x e n a b l e b i t i s s e t i n t h e F P C R , a n d e i t h e r
| inex2 o r i n e x1 o c c u r r e d , w e m u s t c l e a n u p a n d b r a n c h t o t h e
| real i n e x h a n d l e r .
|
ck_inex :
moveb F P C R _ E N A B L E ( % a6 ) ,% d0
andb F P S R _ E X C E P T ( % a6 ) ,% d0
andib #0x3 ,% d0
beq o p e r r _ e x i t
|
| Inexact e n a b l e d a n d r e p o r t e d , a n d w e m u s t t a k e a n i n e x a c t e x c e p t i o n .
|
take_inex :
moveb #I N E X _ V E C , E X C _ V E C + 1 ( % a6 )
movel U S E R _ F P S R ( % a6 ) ,F P S R _ S H A D O W ( % a6 )
orl #s x _ m a s k , E _ B Y T E ( % a 6 )
moveml U S E R _ D A ( % a6 ) ,% d0 - % d1 / % a0 - % a1
fmovemx U S E R _ F P 0 ( % a6 ) ,% f p0 - % f p3
fmoveml U S E R _ F P C R ( % a6 ) ,% f p c r / % f p s r / % f p i a r
frestore ( % a7 ) +
unlk % a6
bral r e a l _ i n e x
|
| Since o p e r r i s o n l y a n E 1 e x c e p t i o n , t h e r e i s n o n e e d t o f r e s t o r e
| any s t a t e b a c k t o t h e f p u .
|
operr_exit :
moveml U S E R _ D A ( % a6 ) ,% d0 - % d1 / % a0 - % a1
fmovemx U S E R _ F P 0 ( % a6 ) ,% f p0 - % f p3
fmoveml U S E R _ F P C R ( % a6 ) ,% f p c r / % f p s r / % f p i a r
unlk % a6
bral f p s p _ d o n e
| end