fenv 4.52 KB
Newer Older
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23
; Copyright 2002 Pace Micro Technology plc
;
; Licensed under the Apache License, Version 2.0 (the "License");
; you may not use this file except in compliance with the License.
; You may obtain a copy of the License at
;
;     http://www.apache.org/licenses/LICENSE-2.0
;
; Unless required by applicable law or agreed to in writing, software
; distributed under the License is distributed on an "AS IS" BASIS,
; WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
; See the License for the specific language governing permissions and
; limitations under the License.
;
FE_INVALID      * &01
FE_DIVBYZERO    * &02
FE_OVERFLOW     * &04
FE_UNDERFLOW    * &08
FE_INEXACT      * &10
FE_ALL_EXCEPT   * &1F

FE_TONEAREST    * 0

Kevin Bracey's avatar
Kevin Bracey committed
24 25 26
FE_Trap_pos     * 16
FE_Flag_pos     * 0

27 28
FE_DFL_ENV      * 0

Kevin Bracey's avatar
Kevin Bracey committed
29 30
FE_Default_FPSR * (FE_INVALID+FE_DIVBYZERO+FE_OVERFLOW) :SHL: FE_Trap_pos

31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91
        GET objmacs.s

        CodeArea

; int feclearexcept(int excepts)
        Function feclearexcept, leaf
        RFS     ip
        AND     a2, a1, #FE_ALL_EXCEPT
        BIC     ip, ip, a2
        WFS     ip
        BIC     a1, a1, #FE_ALL_EXCEPT
        Return  ,,LinkNotStacked

; int fegetexceptflag(fexcept_t *flagp, int excepts)
        Function fegetexceptflag, leaf
        RFS     ip
        AND     a3, a2, #FE_ALL_EXCEPT
        AND     ip, ip, a3
        STR     ip, [a1]
        BIC     a1, a2, #FE_ALL_EXCEPT
        Return  ,,LinkNotStacked

; int fesetexceptflag(const fexcept_t *flagp, int excepts)
        Function fesetexceptflag, leaf
        RFS     ip
        LDR     a1, [a1]
        AND     a3, a2, #FE_ALL_EXCEPT
        AND     a1, a1, a3
        BIC     ip, ip, a3
        ORR     ip, ip, a1
        WFS     ip
        BIC     a1, a2, #FE_ALL_EXCEPT
        Return  ,,LinkNotStacked

; int fetestexcept(int excepts);
        Function fetestexcept, leaf
        RFS     ip
        AND     a1, a1, #FE_ALL_EXCEPT
        AND     a1, ip, a1
        Return  ,,LinkNotStacked

; int fegetround(void)
        Function fegetround, leaf
        MOV     a1, #FE_TONEAREST
        Return  ,,LinkNotStacked

; int fesetround(int round)
        Function fesetround, leaf
        EOR     a1, a1, #FE_TONEAREST
        Return  ,,LinkNotStacked

;int fegetenv(fenv_t *envp)
        Function fegetenv, leaf
        RFS     ip
        STR     ip, [a1]
        Return  ,,LinkNotStacked

; int feholdexcept(fenv_t *envp)
        Function feholdexcept, leaf
        RFS     ip
        STR     ip, [a1]
Kevin Bracey's avatar
Kevin Bracey committed
92 93
        BIC     ip, ip, #FE_ALL_EXCEPT :SHL: FE_Flag_pos
        BIC     ip, ip, #FE_ALL_EXCEPT :SHL: FE_Trap_pos
94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134
        WFS     ip
        MOV     a1, #0
        Return  ,,LinkNotStacked

; int fesetenv(const fenv_t *envp)
        Function fesetenv, leaf
        TEQ     a1, #FE_DFL_ENV
        LDRNE   ip, [a1]
        MOVEQ   ip, #&00070000
        WFS     ip
        RFS     a1
        EOR     a1, a1, ip
        BIC     a1, a1, #&FF000000
        Return  ,,LinkNotStacked

; int feupdateenv(const fenv_t *envp)
        Function feupdateenv, leaf
        TEQ     a1, #FE_DFL_ENV
        LDRNE   ip, [a1]
        MOVEQ   ip, #&00070000
        RFS     a4                      ; read current status
        WFS     ip                      ; write new status
        RFS     a3                      ; check we wrote it successfully
        EOR     a3, a3, ip
        BICS    a1, a3, #&FF000000
        Return  ,,LinkNotStacked, NE    ; return nonzero if not
        AND     a1, a4, #FE_ALL_EXCEPT  ; a1 := previous exceptions
        ; fall through

; int feraiseexcept(int excepts)
        Function feraiseexcept, leaf
        ; Yuck. No easy way to do this. We need five sums that
        ; will generate each exception in turn.
        TST     a1, #FE_INVALID
        MVFNES  f0, #0
        DVFNES  f0, f0, #0
        TST     a1, #FE_DIVBYZERO
        MVFNES  f0, #1
        DVFNES  f0, f0, #0
        TST     a1, #FE_OVERFLOW
        LDFNES  f0, Huge
135
        MUFNES  f0, f0, #2              ; also generates inexact (allowed)
Kevin Bracey's avatar
Kevin Bracey committed
136
        BICNE   a1, a1, #FE_INEXACT
137 138
        TST     a1, #FE_UNDERFLOW
        LDFNES  f0, Tiny
139
        MUFNES  f0, f0, #0.5            ; also generates inexact (allowed)
Kevin Bracey's avatar
Kevin Bracey committed
140
        BICNE   a1, a1, #FE_INEXACT
141 142 143 144 145 146 147 148 149
        TST     a1, #FE_INEXACT
        LDFNES  f0, TwoToTwentyEight
        ADFNES  f0, f0, #1
        BIC     a1, a1, #FE_ALL_EXCEPT
        Return  ,,LinkNotStacked

TwoToTwentyEight
        DCD     &4D800000               ; 1.0 x 2^28
Tiny
150
        DCD     &00000001               ; smallest (subnormal) single
151
Huge
152
        DCD     &7F7FFFFF               ; largest single
153 154

        END