| /* Copyright 2017 The ChromiumOS Authors |
| * Use of this source code is governed by a BSD-style license that can be |
| * found in the LICENSE file. |
| */ |
| |
| #include "config_chip.h" |
| |
| /* |
| * DLMB register = 0x80189: |
| * Disable all interrupts and switching CPU's |
| * ALU (Arithmetic Logic Unit) to floating point operation mode. |
| * (IEEE standard 754 floating point) |
| * |
| * DLMB register = 0x80009: |
| * Restore interrupts and ALU. |
| */ |
| .text |
| .align 2 |
| .global __addsf3 |
| .type __addsf3, @function |
| __addsf3: |
| sethi $r2, 0x80 /* r2 = 0x80000 */ |
| addi $r3, $r2, 0x189 /* r3 = 0x80189 */ |
| addi45 $r2, 0x9 /* r2 = 0x80009 */ |
| mtsr $r3, $dlmb /* dlmb = 0x80189 */ |
| dsb |
| /* Floating-point addition single-precision */ |
| add45 $r0, $r1 |
| mtsr $r2, $dlmb /* dlmb = 0x80009 */ |
| dsb |
| ret5 $lp |
| .size __addsf3, .-__addsf3 |
| |
| .text |
| .align 2 |
| .global __subsf3 |
| .type __subsf3, @function |
| __subsf3: |
| sethi $r2, 0x80 /* r2 = 0x80000 */ |
| addi $r3, $r2, 0x189 /* r3 = 0x80189 */ |
| addi45 $r2, 0x9 /* r2 = 0x80009 */ |
| mtsr $r3, $dlmb /* dlmb = 0x80189 */ |
| dsb |
| /* Floating-point subtraction single-precision */ |
| sub45 $r0, $r1 |
| mtsr $r2, $dlmb /* dlmb = 0x80009 */ |
| dsb |
| ret5 $lp |
| .size __subsf3, .-__subsf3 |
| |
| .text |
| .align 2 |
| .global __mulsf3 |
| .type __mulsf3, @function |
| __mulsf3: |
| #ifdef IT83XX_FPU_MUL_BY_DIV |
| #define SIGN $r2 |
| #define EXPOA $r3 |
| #define MANTA $r4 |
| #define VALUA $r5 |
| #define EXPOB $r6 |
| #define MANTB $r7 |
| #define VALUB $r8 |
| #define SPROD $r15 |
| /* save r6-r8 */ |
| smw.adm $r6, [$sp], $r8, #0x0 |
| xor SPROD, $r1, $r0 /* sign(A xor B) */ |
| move SIGN, #0x80000000 |
| and SPROD, SPROD, SIGN /* store sign bit */ |
| slli VALUA, $r0, 1 /* A<<1, (exponent and mantissa) */ |
| slli VALUB, $r1, 1 /* B<<1, (exponent and mantissa) */ |
| srli EXPOA, VALUA, 24 /* exponent(A) */ |
| srli EXPOB, VALUB, 24 /* exponent(B) */ |
| slli MANTA, VALUA, 7 /* A<<8, mantissa(A) with exponent's LSB */ |
| slli MANTB, VALUB, 7 /* A<<8, mantissa(B) with exponent's LSB */ |
| beqz VALUA, .LFzeroA /* exponent(A) and mantissa (A) are zero */ |
| beqc EXPOA, 0xff, .LFinfnanA /* A is inf or NaN */ |
| beqz VALUB, .LFzeroB /* exponent(B) and mantissa (B) are zero */ |
| beqc EXPOB, 0xff, .LFinfnanB /* B is inf or NaN */ |
| /* A*B = A/(1/B) */ |
| sethi $r2, 0x80 /* r2 = 0x80000 */ |
| addi $r3, $r2, 0x189 /* r3 = 0x80189 */ |
| addi45 $r2, 0x9 /* r2 = 0x80009 */ |
| mtsr $r3, $dlmb /* dlmb = 0x80189 */ |
| dsb |
| sethi $r5, #0x3f800 /* r5 = 1.0f */ |
| divsr $r1,$r1,$r5,$r1 /* r1 = 1.0f / r1 */ |
| divsr $r0,$r0,$r0,$r1 /* r0 = r0 / r1 */ |
| mtsr $r2, $dlmb /* dlmb = 0x80009 */ |
| dsb |
| .LFret: |
| /* restore r6-r8 */ |
| lmw.bim $r6, [$sp], $r8, #0x0 |
| ret5 $lp |
| |
| .LFzeroA: /* A is zero */ |
| beqc EXPOB, 0xff, .LFnan/*zero * inf = zero * NaN = NaN */ |
| .LFzero: |
| move $r0, SPROD /* return 0.0f or -0.0f */ |
| b .LFret |
| .LFinfnanA: /* exponent(A) is 0xff */ |
| bne MANTA, SIGN, .LFnan/* A is NaN: NaN * B = NaN */ |
| beqz VALUB, .LFnan /* A is inf and B is zero: inf * zero = NaN */ |
| bnec EXPOB, 0xff, .LFinf/* B is finite: inf * B = inf */ |
| .LFinfnanB: /* exponent(B) is 0xff */ |
| bne MANTB, SIGN, .LFnan/* B is NaN: A * NaN = NaN */ |
| .LFinf: |
| move $r0, #0x7f800000 |
| or $r0, $r0, SPROD /* return inf or -inf */ |
| b .LFret |
| .LFzeroB: /* B is zero and A is finit */ |
| b .LFzero /* B is zero */ |
| .LFnan: |
| move $r0, #0xffc00000 /* return NaN */ |
| b .LFret |
| #else /* !IT83XX_FPU_MUL_BY_DIV */ |
| sethi $r2, 0x80 /* r2 = 0x80000 */ |
| addi $r3, $r2, 0x189 /* r3 = 0x80189 */ |
| addi45 $r2, 0x9 /* r2 = 0x80009 */ |
| mtsr $r3, $dlmb /* dlmb = 0x80189 */ |
| dsb |
| /* Floating-point multiplication single-precision */ |
| mul33 $r0, $r1 |
| mtsr $r2, $dlmb /* dlmb = 0x80009 */ |
| dsb |
| ret5 $lp |
| #endif /* IT83XX_FPU_MUL_BY_DIV */ |
| .size __mulsf3, .-__mulsf3 |
| |
| .text |
| .align 2 |
| .global __divsf3 |
| .type __divsf3, @function |
| __divsf3: |
| sethi $r2, 0x80 /* r2 = 0x80000 */ |
| addi $r3, $r2, 0x189 /* r3 = 0x80189 */ |
| addi45 $r2, 0x9 /* r2 = 0x80009 */ |
| mtsr $r3, $dlmb /* dlmb = 0x80189 */ |
| dsb |
| /* Floating-point division single-precision */ |
| divsr $r0,$r0,$r0,$r1 |
| mtsr $r2, $dlmb /* dlmb = 0x80009 */ |
| dsb |
| ret5 $lp |
| .size __divsf3, .-__divsf3 |