www.pudn.com > leon3.rar > fpu.c
#include "leon3.h" #include "testmod.h" //#includeint __errno; fputest() { int tmp; tmp = xgetpsr(); setpsr(tmp | (1 << 12)); tmp = xgetpsr(); if (!(tmp & (1 <<12))) return(0); set_fsr(0); report_subtest(FPU_TEST+(get_pid()<<4)); fpu_main(); } asm( " .global a1, a2\n" " .align 8\n" "a1: .word 0x48000001\n" " .word 0\n" "b1: .word 0x48000000\n" " .word 0\n" "c1: .word 0x46c00000\n" " .word 0\n" "c2: .word 0x3ff00000\n" " .word 0 \n" " .word 0x40000000\n" " .word 0 \n" " .word 0x40080000\n" " .word 0 \n" ); asm( " .global \n" " .text \n" " .align 4 \n" " \n" "fpu_chkft: \n" " set 0, %o0 \n" " mov %asr16, %o2 \n" " srl %o2, 30, %o2 \n" " and %o2, 3, %o2 \n" " cmp %o2, %g0 \n" " beq 1f \n" " set c2, %o1 \n" " ldd [%o1], %f0 \n" " ldd [%o1 + 8], %f2 \n" " set 0x03007a, %o2 \n" " mov %o2, %asr16 \n" " nop; nop; nop; nop; nop; nop; \n" " fmovs %f0, %f0 \n" " fmovs %f1, %f1 \n" " set 0x03007e, %o2 \n" " mov %o2, %asr16 \n" " nop; nop; nop; nop; nop; nop; \n" " fmovs %f2, %f2 \n" " fmovs %f3, %f3 \n" " mov %g0, %asr16 \n" " nop; nop; nop; nop; nop; nop; \n" " faddd %f0, %f2, %f4 \n" " ldd [%o1 + 0x10], %f6 \n" " fcmpd %f4, %f6 \n" " nop \n" " fbne,a 1f \n" " set 1, %o0 \n" " mov %asr16, %o1 \n" " srl %o1, 27, %o1 \n" " and %o1, 7, %o1 \n" " sub %o1, 4, %o0 \n" "1: retl \n" " nop \n" ); fpu_main() { volatile double a, c, d; double e; extern volatile double a1,b1,c1; float b; int tmp; d = 3.0; e = d; a = *(double *)&a1 - *(double *)&b1; if (a != c1) fail(1); a = sqrt(e); if (fabs((a * a) - d) > 1E-15) fail(2); b = sqrt(e); if (fabs((b * b) - d) > 1E-7) fail(3); tmp = fpu_pipe(); if (tmp) fail(tmp); tmp = fpu_chkft(); if (tmp) fail(5); } float f1x = -1.0; int fsr1[4] = { 0x80000000, 0 , 0, 0 }; fpu_pipe() { asm( " set fsr1, %o0 ! check ldfsr/stfsr interlock\n" " ld [%o0], %fsr\n" " st %g0, [%o0]\n" " ld [%o0], %fsr\n" " st %fsr, [%o0]\n" " ld [%o0], %o2\n" " set 0x000E0000, %o1\n" " andn %o2, %o1, %o2\n" " subcc %g0, %o2, %g0\n" " bne,a 1f\n" " mov 3, %o0\n" "\n" " set 0x0f800000, %o1 ! check ldfsr/fpop interlock\n" " st %o1, [%sp-96]\n" " st %g0, [%sp-92]\n" " ld [%sp-96], %fsr\n" " st %g0, [%sp-96]\n" " set f1x, %o2\n" " ld [%o2], %f0\n" " nop; nop\n" " ld [%sp-96], %fsr\n" " ld [%sp-92], %fsr\n" " fsqrts %f0, %f1\n" " st %fsr, [%sp-96]\n" " ld [%sp-96], %o0\n" " andcc %o0, 0x200, %g0\n" " be,a 1f\n" " mov 4, %o0\n" "\n" "\n" " mov 0, %o0\n" "\n" "1:\n" " mov %o0, %i0\n" " nop\n" ); } asm ( " .global set_fsr, get_fsr\n" "get_fsr: \n" " st %fsr, [%sp-96]\n" " retl\n" " ld [%sp-96], %o0\n" "set_fsr: \n" " st %o0, [%sp-96]\n" " retl\n" " ld [%sp-96], %fsr\n" );