Linux Kernel
3.7.1
Main Page
Related Pages
Modules
Namespaces
Data Structures
Files
File List
Globals
All
Data Structures
Namespaces
Files
Functions
Variables
Typedefs
Enumerations
Enumerator
Macros
Groups
Pages
arch
parisc
math-emu
dfcmp.c
Go to the documentation of this file.
1
/*
2
* Linux/PA-RISC Project (http://www.parisc-linux.org/)
3
*
4
* Floating-point emulation code
5
* Copyright (C) 2001 Hewlett-Packard (Paul Bame) <
[email protected]
>
6
*
7
* This program is free software; you can redistribute it and/or modify
8
* it under the terms of the GNU General Public License as published by
9
* the Free Software Foundation; either version 2, or (at your option)
10
* any later version.
11
*
12
* This program is distributed in the hope that it will be useful,
13
* but WITHOUT ANY WARRANTY; without even the implied warranty of
14
* MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
15
* GNU General Public License for more details.
16
*
17
* You should have received a copy of the GNU General Public License
18
* along with this program; if not, write to the Free Software
19
* Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
20
*/
21
/*
22
* BEGIN_DESC
23
*
24
* File:
25
* @(#) pa/spmath/dfcmp.c $Revision: 1.1 $
26
*
27
* Purpose:
28
* dbl_cmp: compare two values
29
*
30
* External Interfaces:
31
* dbl_fcmp(leftptr, rightptr, cond, status)
32
*
33
* Internal Interfaces:
34
*
35
* Theory:
36
* <<please update with a overview of the operation of this file>>
37
*
38
* END_DESC
39
*/
40
41
42
43
#include "
float.h
"
44
#include "
dbl_float.h
"
45
46
/*
47
* dbl_cmp: compare two values
48
*/
49
int
50
dbl_fcmp
(
dbl_floating_point
* leftptr,
dbl_floating_point
* rightptr,
51
unsigned
int
cond
,
unsigned
int
*
status
)
52
53
/* The predicate to be tested */
54
55
{
56
register
unsigned
int
leftp1, leftp2, rightp1, rightp2;
57
register
int
xorresult;
58
59
/* Create local copies of the numbers */
60
Dbl_copyfromptr
(leftptr,leftp1,leftp2);
61
Dbl_copyfromptr
(rightptr,rightp1,rightp2);
62
/*
63
* Test for NaN
64
*/
65
if
( (
Dbl_exponent
(leftp1) ==
DBL_INFINITY_EXPONENT
)
66
|| (
Dbl_exponent
(rightp1) ==
DBL_INFINITY_EXPONENT
) )
67
{
68
/* Check if a NaN is involved. Signal an invalid exception when
69
* comparing a signaling NaN or when comparing quiet NaNs and the
70
* low bit of the condition is set */
71
if
( ((
Dbl_exponent
(leftp1) ==
DBL_INFINITY_EXPONENT
)
72
&&
Dbl_isnotzero_mantissa
(leftp1,leftp2)
73
&& (
Exception
(cond) ||
Dbl_isone_signaling
(leftp1)))
74
||
75
((
Dbl_exponent
(rightp1) ==
DBL_INFINITY_EXPONENT
)
76
&&
Dbl_isnotzero_mantissa
(rightp1,rightp2)
77
&& (
Exception
(cond) ||
Dbl_isone_signaling
(rightp1))) )
78
{
79
if
(
Is_invalidtrap_enabled
() ) {
80
Set_status_cbit
(
Unordered
(cond));
81
return
(
INVALIDEXCEPTION
);
82
}
83
else
Set_invalidflag
();
84
Set_status_cbit
(
Unordered
(cond));
85
return
(
NOEXCEPTION
);
86
}
87
/* All the exceptional conditions are handled, now special case
88
NaN compares */
89
else
if
( ((
Dbl_exponent
(leftp1) ==
DBL_INFINITY_EXPONENT
)
90
&&
Dbl_isnotzero_mantissa
(leftp1,leftp2))
91
||
92
((
Dbl_exponent
(rightp1) ==
DBL_INFINITY_EXPONENT
)
93
&&
Dbl_isnotzero_mantissa
(rightp1,rightp2)) )
94
{
95
/* NaNs always compare unordered. */
96
Set_status_cbit
(
Unordered
(cond));
97
return
(
NOEXCEPTION
);
98
}
99
/* infinities will drop down to the normal compare mechanisms */
100
}
101
/* First compare for unequal signs => less or greater or
102
* special equal case */
103
Dbl_xortointp1
(leftp1,rightp1,xorresult);
104
if
( xorresult < 0 )
105
{
106
/* left negative => less, left positive => greater.
107
* equal is possible if both operands are zeros. */
108
if
(
Dbl_iszero_exponentmantissa
(leftp1,leftp2)
109
&&
Dbl_iszero_exponentmantissa
(rightp1,rightp2) )
110
{
111
Set_status_cbit
(
Equal
(cond));
112
}
113
else
if
(
Dbl_isone_sign
(leftp1) )
114
{
115
Set_status_cbit
(
Lessthan
(cond));
116
}
117
else
118
{
119
Set_status_cbit
(
Greaterthan
(cond));
120
}
121
}
122
/* Signs are the same. Treat negative numbers separately
123
* from the positives because of the reversed sense. */
124
else
if
(
Dbl_isequal
(leftp1,leftp2,rightp1,rightp2))
125
{
126
Set_status_cbit
(
Equal
(cond));
127
}
128
else
if
(
Dbl_iszero_sign
(leftp1) )
129
{
130
/* Positive compare */
131
if
(
Dbl_allp1
(leftp1) <
Dbl_allp1
(rightp1) )
132
{
133
Set_status_cbit
(
Lessthan
(cond));
134
}
135
else
if
(
Dbl_allp1
(leftp1) >
Dbl_allp1
(rightp1) )
136
{
137
Set_status_cbit
(
Greaterthan
(cond));
138
}
139
else
140
{
141
/* Equal first parts. Now we must use unsigned compares to
142
* resolve the two possibilities. */
143
if
(
Dbl_allp2
(leftp2) <
Dbl_allp2
(rightp2) )
144
{
145
Set_status_cbit
(
Lessthan
(cond));
146
}
147
else
148
{
149
Set_status_cbit
(
Greaterthan
(cond));
150
}
151
}
152
}
153
else
154
{
155
/* Negative compare. Signed or unsigned compares
156
* both work the same. That distinction is only
157
* important when the sign bits differ. */
158
if
(
Dbl_allp1
(leftp1) >
Dbl_allp1
(rightp1) )
159
{
160
Set_status_cbit
(
Lessthan
(cond));
161
}
162
else
if
(
Dbl_allp1
(leftp1) <
Dbl_allp1
(rightp1) )
163
{
164
Set_status_cbit
(
Greaterthan
(cond));
165
}
166
else
167
{
168
/* Equal first parts. Now we must use unsigned compares to
169
* resolve the two possibilities. */
170
if
(
Dbl_allp2
(leftp2) >
Dbl_allp2
(rightp2) )
171
{
172
Set_status_cbit
(
Lessthan
(cond));
173
}
174
else
175
{
176
Set_status_cbit
(
Greaterthan
(cond));
177
}
178
}
179
}
180
return
(
NOEXCEPTION
);
181
}
Generated on Thu Jan 10 2013 13:12:58 for Linux Kernel by
1.8.2