OpenCores
URL https://opencores.org/ocsvn/openrisc_me/openrisc_me/trunk

Subversion Repositories openrisc_me

[/] [openrisc/] [trunk/] [gnu-src/] [gdb-6.8/] [sim/] [erc32/] [float.c] - Blame information for rev 247

Go to most recent revision | Details | Compare with Previous | View Log

Line No. Rev Author Line
1 24 jeremybenn
/*
2
 * This file is part of SIS.
3
 *
4
 * SIS, SPARC instruction simulator. Copyright (C) 1995 Jiri Gaisler, European
5
 * Space Agency
6
 *
7
 * This program is free software; you can redistribute it and/or modify it under
8
 * the terms of the GNU General Public License as published by the Free
9
 * Software Foundation; either version 2 of the License, or (at your option)
10
 * any later version.
11
 *
12
 * This program is distributed in the hope that it will be useful, but WITHOUT
13
 * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
14
 * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License for
15
 * more details.
16
 *
17
 * You should have received a copy of the GNU General Public License along with
18
 * this program; if not, write to the Free Software Foundation, Inc., 675
19
 * Mass Ave, Cambridge, MA 02139, USA.
20
 *
21
 *
22
 * This file implements the interface between the host and the simulated
23
 * FPU. IEEE trap handling is done as follows:
24
 * 1. In the host, all IEEE traps are masked
25
 * 2. After each simulated FPU instruction, check if any exception occured
26
 *    by reading the exception bits from the host FPU status register
27
 *    (get_accex()).
28
 * 3. Propagate any exceptions to the simulated FSR.
29
 * 4. Clear host exception bits
30
 *
31
 *
32
 * This can also be done using ieee_flags() library routine on sun.
33
 */
34
 
35
#include "sis.h"
36
 
37
/* Forward declarations */
38
 
39
extern uint32   _get_sw PARAMS ((void));
40
extern uint32   _get_cw PARAMS ((void));
41
static void     __setfpucw PARAMS ((unsigned short fpu_control));
42
 
43
/* This host dependent routine should return the accrued exceptions */
44
int
45
get_accex()
46
{
47
#ifdef sparc
48
    return ((_get_fsr_raw() >> 5) & 0x1F);
49
#elif i386
50
    uint32 accx;
51
 
52
    accx = _get_sw() & 0x3f;
53
    accx = ((accx & 1) << 4) | ((accx & 2) >> 1) | ((accx & 4) >> 1) |
54
           (accx & 8) | ((accx & 16) >> 2) | ((accx & 32) >> 5);
55
    return(accx);
56
#else
57
    return(0);
58
#warning no fpu trap support for this target
59
#endif
60
 
61
}
62
 
63
/* How to clear the accrued exceptions */
64
void
65
clear_accex()
66
{
67
#ifdef sparc
68
    set_fsr((_get_fsr_raw() & ~0x3e0));
69
#elif i386
70
    asm("\n"
71
".text\n"
72
"       fnclex\n"
73
"\n"
74
"    ");
75
#else
76
#warning no fpu trap support for this target
77
#endif
78
}
79
 
80
/* How to map SPARC FSR onto the host */
81
void
82
set_fsr(fsr)
83
uint32 fsr;
84
{
85
#ifdef sparc
86
        _set_fsr_raw(fsr & ~0x0f800000);
87
#elif i386
88
     void __setfpucw(unsigned short fpu_control);
89
     uint32 rawfsr;
90
 
91
     fsr >>= 30;
92
     switch (fsr) {
93
        case 0:
94
        case 2: break;
95
        case 1: fsr = 3;
96
        case 3: fsr = 1;
97
     }
98
     rawfsr = _get_cw();
99
     rawfsr |= (fsr << 10) | 0x3ff;
100
     __setfpucw(rawfsr);
101
#else
102
#warning no fpu trap support for this target
103
#endif
104
}
105
 
106
 
107
/* Host dependent support functions */
108
 
109
#ifdef sparc
110
 
111
    asm("\n"
112
"\n"
113
".text\n"
114
"        .align 4\n"
115
"        .global __set_fsr_raw,_set_fsr_raw\n"
116
"__set_fsr_raw:\n"
117
"_set_fsr_raw:\n"
118
"        save %sp,-104,%sp\n"
119
"        st %i0,[%fp+68]\n"
120
"        ld [%fp+68], %fsr\n"
121
"        mov 0,%i0\n"
122
"        ret\n"
123
"        restore\n"
124
"\n"
125
"        .align 4\n"
126
"        .global __get_fsr_raw\n"
127
"        .global _get_fsr_raw\n"
128
"__get_fsr_raw:\n"
129
"_get_fsr_raw:\n"
130
"        save %sp,-104,%sp\n"
131
"        st %fsr,[%fp+68]\n"
132
"        ld [%fp+68], %i0\n"
133
"        ret\n"
134
"        restore\n"
135
"\n"
136
"    ");
137
 
138
#elif i386
139
 
140
    asm("\n"
141
"\n"
142
".text\n"
143
"        .align 8\n"
144
".globl _get_sw,__get_sw\n"
145
"__get_sw:\n"
146
"_get_sw:\n"
147
"        pushl %ebp\n"
148
"        movl %esp,%ebp\n"
149
"        movl $0,%eax\n"
150
"        fnstsw %ax\n"
151
"        movl %ebp,%esp\n"
152
"        popl %ebp\n"
153
"        ret\n"
154
"\n"
155
"        .align 8\n"
156
".globl _get_cw,__get_cw\n"
157
"__get_cw:\n"
158
"_get_cw:\n"
159
"        pushl %ebp\n"
160
"        movl %esp,%ebp\n"
161
"        subw $2,%esp\n"
162
"        fnstcw -2(%ebp)\n"
163
"        movw -2(%ebp),%eax\n"
164
"        movl %ebp,%esp\n"
165
"        popl %ebp\n"
166
"        ret\n"
167
"\n"
168
"\n"
169
"    ");
170
 
171
 
172
#else
173
#warning no fpu trap support for this target
174
#endif
175
 
176
#if i386
177
/* #if defined _WIN32 || defined __GO32__ */
178
/* This is so floating exception handling works on NT
179
   These definitions are from the linux fpu_control.h, which
180
   doesn't exist on NT.
181
 
182
   default to:
183
     - extended precision
184
     - rounding to nearest
185
     - exceptions on overflow, zero divide and NaN
186
*/
187
#define _FPU_DEFAULT  0x1372 
188
#define _FPU_RESERVED 0xF0C0  /* Reserved bits in cw */
189
 
190
static void
191
__setfpucw(unsigned short fpu_control)
192
{
193
  volatile unsigned short cw;
194
 
195
  /* If user supplied _fpu_control, use it ! */
196
  if (!fpu_control)
197
  {
198
    /* use defaults */
199
    fpu_control = _FPU_DEFAULT;
200
  }
201
  /* Get Control Word */
202
  __asm__ volatile ("fnstcw %0" : "=m" (cw) : );
203
 
204
  /* mask in */
205
  cw &= _FPU_RESERVED;
206
  cw = cw | (fpu_control & ~_FPU_RESERVED);
207
 
208
  /* set cw */
209
  __asm__ volatile ("fldcw %0" :: "m" (cw));
210
}
211
/* #endif */
212
#endif

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.