annotate packages/hal/mips/arch/current/src/mipsfp.c @ 26:4741a3c3496a ecos-sw-1999-07-23

Merge from eCos master repository on 1999-07-23-05:47:06-BST
author jlarmour
date Fri, 23 Jul 1999 15:20:15 +0000
parents
children 641b639be825
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
26
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
1 //==========================================================================
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
2 //
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
3 // mipsfp.c
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
4 //
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
5 // HAL miscellaneous functions
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
6 //
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
7 //==========================================================================
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
8 //####COPYRIGHTBEGIN####
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
9 //
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
10 // -------------------------------------------
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
11 // The contents of this file are subject to the Cygnus eCos Public License
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
12 // Version 1.0 (the "License"); you may not use this file except in
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
13 // compliance with the License. You may obtain a copy of the License at
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
14 // http://sourceware.cygnus.com/ecos
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
15 //
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
16 // Software distributed under the License is distributed on an "AS IS"
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
17 // basis, WITHOUT WARRANTY OF ANY KIND, either express or implied. See the
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
18 // License for the specific language governing rights and limitations under
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
19 // the License.
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
20 //
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
21 // The Original Code is eCos - Embedded Cygnus Operating System, released
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
22 // September 30, 1998.
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
23 //
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
24 // The Initial Developer of the Original Code is Cygnus. Portions created
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
25 // by Cygnus are Copyright (C) 1998,1999 Cygnus Solutions. All Rights Reserved.
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
26 // -------------------------------------------
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
27 //
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
28 //####COPYRIGHTEND####
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
29 //==========================================================================
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
30 //#####DESCRIPTIONBEGIN####
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
31 //
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
32 // Author(s): jlarmour
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
33 // Contributors: jlarmour
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
34 // Date: 1999-07-13
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
35 // Purpose: Emulate unimplemented FP operations on MIPS architectures
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
36 // Description: This catches the unimplemented operation excetion only,
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
37 // and if possible deals with it so processing can continue
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
38 // as if the MIPS had a proper IEEE FPU
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
39 //
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
40 //
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
41 //####DESCRIPTIONEND####
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
42 //
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
43 //========================================================================*/
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
44
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
45 // CONFIGURATION
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
46
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
47 #include <pkgconf/hal.h>
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
48
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
49 #ifdef CYGHWR_HAL_MIPS_FPU
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
50
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
51 // INCLUDES
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
52
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
53 #include <cyg/infra/cyg_type.h> // Standard eCos types
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
54 #include <cyg/infra/cyg_ass.h> // Standard eCos assertion support
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
55 #include <cyg/infra/cyg_trac.h> // Standard eCos tracing support
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
56 #include <cyg/hal/hal_intr.h> // HAL interrupt vectors
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
57 #include <cyg/hal/hal_arch.h> // Architecture types such as
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
58 // HAL_SavedRegisters
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
59 #define CYGARC_HAL_COMMON_EXPORT_CPU_MACROS
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
60 #include <cyg/hal/mips-regs.h> // MIPS register and bitmask definitions
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
61
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
62 // TYPES
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
63
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
64 // The following types were taken from <sys/ieeefp.h> from libm.
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
65
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
66 #if (CYG_BYTEORDER == CYG_MSBFIRST) // Big endian
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
67
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
68 // Note: there do not seem to be any current machines which are Big Endian but
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
69 // have a mixed up double layout.
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
70
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
71 typedef union
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
72 {
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
73 cyg_int32 asi32[2];
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
74
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
75 cyg_int64 asi64;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
76
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
77 double value;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
78
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
79 struct
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
80 {
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
81 unsigned int sign : 1;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
82 unsigned int exponent: 11;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
83 unsigned int fraction0:4;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
84 unsigned int fraction1:16;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
85 unsigned int fraction2:16;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
86 unsigned int fraction3:16;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
87
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
88 } number;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
89
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
90 struct
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
91 {
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
92 unsigned int sign : 1;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
93 unsigned int exponent: 11;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
94 unsigned int quiet:1;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
95 unsigned int function0:3;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
96 unsigned int function1:16;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
97 unsigned int function2:16;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
98 unsigned int function3:16;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
99 } nan;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
100
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
101 struct
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
102 {
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
103 cyg_uint32 msw;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
104 cyg_uint32 lsw;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
105 } parts;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
106
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
107
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
108 } Cyg_libm_ieee_double_shape_type;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
109
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
110
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
111 typedef union
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
112 {
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
113 cyg_int32 asi32;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
114
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
115 float value;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
116
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
117 struct
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
118 {
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
119 unsigned int sign : 1;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
120 unsigned int exponent: 8;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
121 unsigned int fraction0: 7;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
122 unsigned int fraction1: 16;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
123 } number;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
124
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
125 struct
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
126 {
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
127 unsigned int sign:1;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
128 unsigned int exponent:8;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
129 unsigned int quiet:1;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
130 unsigned int function0:6;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
131 unsigned int function1:16;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
132 } nan;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
133
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
134 } Cyg_libm_ieee_float_shape_type;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
135
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
136
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
137 #else // Little endian
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
138
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
139 typedef union
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
140 {
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
141 cyg_int32 asi32[2];
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
142
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
143 cyg_int64 asi64;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
144
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
145 double value;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
146
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
147 struct
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
148 {
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
149 #if (CYG_DOUBLE_BYTEORDER == CYG_MSBFIRST) // Big endian
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
150 unsigned int fraction1:16;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
151 unsigned int fraction0: 4;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
152 unsigned int exponent :11;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
153 unsigned int sign : 1;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
154 unsigned int fraction3:16;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
155 unsigned int fraction2:16;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
156 #else
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
157 unsigned int fraction3:16;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
158 unsigned int fraction2:16;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
159 unsigned int fraction1:16;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
160 unsigned int fraction0: 4;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
161 unsigned int exponent :11;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
162 unsigned int sign : 1;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
163 #endif
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
164 } number;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
165
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
166 struct
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
167 {
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
168 #if (CYG_DOUBLE_BYTEORDER == CYG_MSBFIRST) // Big endian
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
169 unsigned int function1:16;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
170 unsigned int function0:3;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
171 unsigned int quiet:1;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
172 unsigned int exponent: 11;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
173 unsigned int sign : 1;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
174 unsigned int function3:16;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
175 unsigned int function2:16;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
176 #else
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
177 unsigned int function3:16;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
178 unsigned int function2:16;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
179 unsigned int function1:16;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
180 unsigned int function0:3;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
181 unsigned int quiet:1;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
182 unsigned int exponent: 11;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
183 unsigned int sign : 1;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
184 #endif
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
185 } nan;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
186
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
187 struct
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
188 {
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
189 #if (CYG_DOUBLE_BYTEORDER == CYG_MSBFIRST) // Big endian
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
190 cyg_uint32 msw;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
191 cyg_uint32 lsw;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
192 #else
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
193 cyg_uint32 lsw;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
194 cyg_uint32 msw;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
195 #endif
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
196 } parts;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
197
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
198 } Cyg_libm_ieee_double_shape_type;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
199
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
200
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
201 typedef union
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
202 {
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
203 cyg_int32 asi32;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
204
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
205 float value;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
206
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
207 struct
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
208 {
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
209 unsigned int fraction0: 7;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
210 unsigned int fraction1: 16;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
211 unsigned int exponent: 8;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
212 unsigned int sign : 1;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
213 } number;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
214
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
215 struct
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
216 {
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
217 unsigned int function1:16;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
218 unsigned int function0:6;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
219 unsigned int quiet:1;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
220 unsigned int exponent:8;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
221 unsigned int sign:1;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
222 } nan;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
223
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
224 } Cyg_libm_ieee_float_shape_type;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
225
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
226 #endif // little-endian
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
227
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
228 typedef enum {
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
229 ADD_INSN=0, // 0
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
230 SUB_INSN,
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
231 MUL_INSN,
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
232 DIV_INSN,
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
233 SQRT_INSN,
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
234 ABS_INSN, // 5
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
235 MOV_INSN,
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
236 NEG_INSN,
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
237 ROUNDL_INSN,
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
238 TRUNCL_INSN,
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
239 CEILL_INSN, // 10
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
240 FLOORL_INSN,
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
241 ROUNDW_INSN,
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
242 TRUNCW_INSN,
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
243 CEILW_INSN,
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
244 FLOORW_INSN, // 15
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
245 // ...
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
246 CVTS_INSN=32,
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
247 CVTD_INSN,
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
248 // ...
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
249 CVTW_INSN=36,
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
250 CVTL_INSN,
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
251 // ...
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
252 //
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
253 // 48-63 are floating point compare - treated separately
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
254
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
255 } fp_operation;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
256
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
257 typedef enum {
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
258 S_FORMAT=16,
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
259 D_FORMAT=17,
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
260 W_FORMAT=20,
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
261 L_FORMAT=21
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
262 } fp_format;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
263
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
264 // FUNCTIONS
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
265
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
266 #define issubnormal(_x_) ((_x_)->number.exponent == 0)
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
267
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
268 // This function returns non-zero if the exception has been handled
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
269 // successfully.
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
270
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
271 // FIXME: Arguably we should raise underflow exceptions in some of the cases
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
272 // below e.g. sqrt(subnormal). And perhaps we should round appropriately to
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
273 // +/- 2^^Emin if round to +/- infinity is enabled, as per the FS bit. Not sure.
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
274
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
275 externC cyg_uint8
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
276 cyg_hal_mips_process_fpe( HAL_SavedRegisters *regs )
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
277 {
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
278 CYG_WORD insn;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
279 CYG_HAL_FPU_REG *srcreg1, *srcreg2, *dstreg;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
280 cyg_uint8 handled=0;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
281 fp_format format;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
282 cyg_uint8 fp64bit=0; // true if format is 64bit, false if 32bit
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
283 cyg_uint8 fixedpoint=0; // true if format is fixed point, false if
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
284 // floating point
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
285 cyg_uint8 computational_insn=1; // computational FP instruction
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
286 cyg_bool delay_slot; // did it happen in a delay slot
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
287
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
288 CYG_CHECK_DATA_PTR( regs,
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
289 "cyg_hal_mips_process_fpe() called with invalid regs ptr");
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
290
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
291 CYG_PRECONDITION( (regs->vector>>2) == CYGNUM_HAL_VECTOR_FPE,
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
292 "Asked to process non-FPE exception");
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
293
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
294 CYG_REPORT_FUNCNAMETYPE("cyg_hal_mips_process_fpe", "returning %d");
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
295
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
296 // First of all, we only handle the unimplemented operation exception
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
297 // here, so if we don't have that, we just exit
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
298 if ((regs->fcr31 & FCR31_CAUSE_E) == 0) {
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
299 CYG_REPORT_RETVAL(0);
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
300 return 0;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
301 }
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
302
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
303 // Get the contents of the instruction that caused the exception. This
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
304 // may have been in a branch delay slot however, so we have to check
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
305 // the BD bit in the cause register first.
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
306 if (regs->cause & CAUSE_BD) {
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
307 insn = *(((CYG_WORD *) regs->pc) + 1);
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
308 delay_slot = true;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
309 } else {
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
310 insn = *(CYG_WORD *) regs->pc;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
311 delay_slot = false;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
312 }
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
313
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
314 CYG_TRACE2(true, "exception at pc %08x containing %08x", regs->pc, insn);
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
315
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
316 CYG_ASSERT( (insn>>26) == 0x11,
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
317 "Instruction at pc doesn't have expected opcode COP1");
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
318
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
319 // Determine the format
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
320 format = (insn >> 21) & 0x1f;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
321
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
322 switch (format)
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
323 {
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
324 case S_FORMAT:
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
325 break;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
326 case D_FORMAT:
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
327 fp64bit++;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
328 break;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
329 case W_FORMAT:
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
330 fixedpoint++;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
331 break;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
332 case L_FORMAT:
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
333 fixedpoint++;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
334 fp64bit++;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
335 break;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
336 default:
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
337 computational_insn=0;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
338 break;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
339 } // switch
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
340
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
341 // This module only emulates computational floating point instructions
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
342 if (computational_insn && !fixedpoint) {
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
343
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
344 // Decode the registers used
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
345 dstreg = &regs->f[ (insn >> 6) & 0x1f ];
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
346 srcreg1 = &regs->f[ (insn >> 11) & 0x1f ];
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
347 srcreg2 = &regs->f[ (insn >> 16) & 0x1f ];
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
348
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
349 // Determine the operation requested
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
350 switch (insn & 0x3f)
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
351 {
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
352 case ADD_INSN:
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
353 case SUB_INSN:
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
354 case MUL_INSN:
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
355 case DIV_INSN:
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
356
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
357 if (fp64bit) {
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
358 Cyg_libm_ieee_double_shape_type *s1, *s2;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
359
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
360 s1 = (Cyg_libm_ieee_double_shape_type *)srcreg1;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
361 s2 = (Cyg_libm_ieee_double_shape_type *)srcreg2;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
362
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
363 if (issubnormal(s1)) { // flush to 0 and restart
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
364 s1->value=0.0;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
365 handled++;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
366 }
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
367
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
368 // We could try flushing both to 0 at the same time, but
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
369 // that's inadvisable if both numbers are very small.
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
370 // Particularly if this is DIV_INSN, when we could therefore
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
371 // get 0/0 even when the program explicitly checked for
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
372 // denominator != 0. That's also why we check s1 first.
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
373
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
374 else if (issubnormal(s2)) { // flush to 0 and restart
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
375 s2->value=0.0;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
376 handled++;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
377 }
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
378 } else { // 32-bit
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
379 Cyg_libm_ieee_float_shape_type *s1, *s2;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
380
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
381 s1 = (Cyg_libm_ieee_float_shape_type *)srcreg1;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
382 s2 = (Cyg_libm_ieee_float_shape_type *)srcreg2;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
383
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
384 if (issubnormal(s1)) { // flush to 0 and restart
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
385 s1->value=0.0;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
386 handled++;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
387 }
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
388 else if (issubnormal(s2)) { // flush to 0 and restart
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
389 s2->value=0.0;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
390 handled++;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
391 }
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
392 }
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
393 break;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
394
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
395 case SQRT_INSN:
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
396 if (fp64bit) {
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
397 Cyg_libm_ieee_double_shape_type *d, *s;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
398
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
399 d = (Cyg_libm_ieee_double_shape_type *)dstreg;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
400 s = (Cyg_libm_ieee_double_shape_type *)srcreg1;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
401
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
402 if (issubnormal(s)) { // Sqrt of something tiny is 0
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
403 // if this is a delay slot, we can't restart properly
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
404 // so clear the source register instead
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
405 if (delay_slot)
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
406 s->value=0.0;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
407 else {
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
408 d->value=0.0;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
409 regs->pc += 4; // We've dealt with this so move on
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
410 }
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
411 handled++;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
412 }
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
413
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
414 } else { // 32-bit
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
415 Cyg_libm_ieee_float_shape_type *d, *s;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
416
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
417 d = (Cyg_libm_ieee_float_shape_type *)dstreg;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
418 s = (Cyg_libm_ieee_float_shape_type *)srcreg1;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
419
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
420 if (issubnormal(s)) { // Sqrt of something tiny is 0
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
421 // if this is a delay slot, we can't restart properly
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
422 // so clear the source register instead
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
423 if (delay_slot)
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
424 s->value=0.0;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
425 else {
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
426 d->value=0.0;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
427 regs->pc += 4; // We've dealt with this so move on
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
428 }
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
429 handled++;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
430 }
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
431 }
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
432 break;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
433
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
434 case ABS_INSN:
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
435 // We may as well do this right if we can
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
436 if (fp64bit) {
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
437 Cyg_libm_ieee_double_shape_type *d, *s;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
438
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
439 d = (Cyg_libm_ieee_double_shape_type *)dstreg;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
440 s = (Cyg_libm_ieee_double_shape_type *)srcreg1;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
441
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
442 // if this is a delay slot, we can't restart properly
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
443 // so clear the source register instead
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
444 if (delay_slot) {
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
445 s->value=0.0;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
446 } else {
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
447 d->asi64 = s->asi64;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
448 d->number.sign = 0;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
449 regs->pc += 4;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
450 }
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
451 } else { // 32-bit
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
452 Cyg_libm_ieee_float_shape_type *d, *s;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
453
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
454 d = (Cyg_libm_ieee_float_shape_type *)dstreg;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
455 s = (Cyg_libm_ieee_float_shape_type *)srcreg1;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
456
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
457 // if this is a delay slot, we can't restart properly
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
458 // so clear the source register instead
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
459 if (delay_slot) {
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
460 s->value=0.0;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
461 } else {
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
462 d->asi32 = s->asi32;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
463 d->number.sign = 0;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
464 regs->pc += 4;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
465 }
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
466 }
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
467 handled++;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
468 break;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
469
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
470 case NEG_INSN:
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
471 // We may as well do this right if we can
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
472 if (fp64bit) {
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
473 Cyg_libm_ieee_double_shape_type *d, *s;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
474
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
475 d = (Cyg_libm_ieee_double_shape_type *)dstreg;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
476 s = (Cyg_libm_ieee_double_shape_type *)srcreg1;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
477
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
478 // if this is a delay slot, we can't restart properly
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
479 // so clear the source register instead
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
480 if (delay_slot) {
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
481 s->value=0.0;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
482 } else {
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
483 d->asi64 = s->asi64;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
484 d->number.sign = s->number.sign ? 0 : 1;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
485 regs->pc += 4;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
486 }
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
487 } else { // 32-bit
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
488 Cyg_libm_ieee_float_shape_type *d, *s;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
489
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
490 d = (Cyg_libm_ieee_float_shape_type *)dstreg;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
491 s = (Cyg_libm_ieee_float_shape_type *)srcreg1;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
492
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
493 // if this is a delay slot, we can't restart properly
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
494 // so clear the source register instead
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
495 if (delay_slot) {
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
496 s->value=0.0;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
497 } else {
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
498 d->asi32 = s->asi32;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
499 d->number.sign = s->number.sign ? 0 : 1;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
500 regs->pc += 4;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
501 }
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
502 }
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
503 handled++;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
504 break;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
505
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
506 default:
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
507 break;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
508 } // switch
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
509
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
510 // As well as all the other opcodes in the enum, there are also all
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
511 // the floating point compare operations between 48 and 63
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
512 }
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
513
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
514 if (handled) {
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
515 // We must clear the cause and flag bits before restoring FPCR31
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
516 regs->fcr31 &= ~(FCR31_CAUSE_E | FCR31_CAUSE_V | FCR31_CAUSE_Z |
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
517 FCR31_CAUSE_O | FCR31_CAUSE_U | FCR31_CAUSE_I |
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
518 FCR31_FLAGS_V | FCR31_FLAGS_Z |
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
519 FCR31_FLAGS_O | FCR31_FLAGS_U | FCR31_FLAGS_I);
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
520
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
521 }
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
522
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
523 CYG_REPORT_RETVAL(handled);
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
524 return handled;
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
525 } // cyg_hal_mips_process_fpe()
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
526
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
527 #endif // ifdef CYGHWR_HAL_MIPS_FPU
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
528
4741a3c3496a Merge from eCos master repository on 1999-07-23-05:47:06-BST
jlarmour
parents:
diff changeset
529 // EOF mipsfp.c