GCC Code Coverage Report
Directory: ./ Exec Total Coverage
File: lib/libcompiler_rt/comparesf2.c Lines: 0 33 0.0 %
Date: 2017-11-07 Branches: 0 28 0.0 %

Line Branch Exec Source
1
//===-- lib/comparesf2.c - Single-precision comparisons -----------*- C -*-===//
2
//
3
//                     The LLVM Compiler Infrastructure
4
//
5
// This file is dual licensed under the MIT and the University of Illinois Open
6
// Source Licenses. See LICENSE.TXT for details.
7
//
8
//===----------------------------------------------------------------------===//
9
//
10
// This file implements the following soft-fp_t comparison routines:
11
//
12
//   __eqsf2   __gesf2   __unordsf2
13
//   __lesf2   __gtsf2
14
//   __ltsf2
15
//   __nesf2
16
//
17
// The semantics of the routines grouped in each column are identical, so there
18
// is a single implementation for each, and wrappers to provide the other names.
19
//
20
// The main routines behave as follows:
21
//
22
//   __lesf2(a,b) returns -1 if a < b
23
//                         0 if a == b
24
//                         1 if a > b
25
//                         1 if either a or b is NaN
26
//
27
//   __gesf2(a,b) returns -1 if a < b
28
//                         0 if a == b
29
//                         1 if a > b
30
//                        -1 if either a or b is NaN
31
//
32
//   __unordsf2(a,b) returns 0 if both a and b are numbers
33
//                           1 if either a or b is NaN
34
//
35
// Note that __lesf2( ) and __gesf2( ) are identical except in their handling of
36
// NaN values.
37
//
38
//===----------------------------------------------------------------------===//
39
40
#define SINGLE_PRECISION
41
#include "fp_lib.h"
42
43
enum LE_RESULT {
44
    LE_LESS      = -1,
45
    LE_EQUAL     =  0,
46
    LE_GREATER   =  1,
47
    LE_UNORDERED =  1
48
};
49
50
COMPILER_RT_ABI enum LE_RESULT
51
__lesf2(fp_t a, fp_t b) {
52
53
    const srep_t aInt = toRep(a);
54
    const srep_t bInt = toRep(b);
55
    const rep_t aAbs = aInt & absMask;
56
    const rep_t bAbs = bInt & absMask;
57
58
    // If either a or b is NaN, they are unordered.
59
    if (aAbs > infRep || bAbs > infRep) return LE_UNORDERED;
60
61
    // If a and b are both zeros, they are equal.
62
    if ((aAbs | bAbs) == 0) return LE_EQUAL;
63
64
    // If at least one of a and b is positive, we get the same result comparing
65
    // a and b as signed integers as we would with a fp_ting-point compare.
66
    if ((aInt & bInt) >= 0) {
67
        if (aInt < bInt) return LE_LESS;
68
        else if (aInt == bInt) return LE_EQUAL;
69
        else return LE_GREATER;
70
    }
71
72
    // Otherwise, both are negative, so we need to flip the sense of the
73
    // comparison to get the correct result.  (This assumes a twos- or ones-
74
    // complement integer representation; if integers are represented in a
75
    // sign-magnitude representation, then this flip is incorrect).
76
    else {
77
        if (aInt > bInt) return LE_LESS;
78
        else if (aInt == bInt) return LE_EQUAL;
79
        else return LE_GREATER;
80
    }
81
}
82
83
#if defined(__ELF__)
84
// Alias for libgcc compatibility
85
FNALIAS(__cmpsf2, __lesf2);
86
#endif
87
88
enum GE_RESULT {
89
    GE_LESS      = -1,
90
    GE_EQUAL     =  0,
91
    GE_GREATER   =  1,
92
    GE_UNORDERED = -1   // Note: different from LE_UNORDERED
93
};
94
95
COMPILER_RT_ABI enum GE_RESULT
96
__gesf2(fp_t a, fp_t b) {
97
98
    const srep_t aInt = toRep(a);
99
    const srep_t bInt = toRep(b);
100
    const rep_t aAbs = aInt & absMask;
101
    const rep_t bAbs = bInt & absMask;
102
103
    if (aAbs > infRep || bAbs > infRep) return GE_UNORDERED;
104
    if ((aAbs | bAbs) == 0) return GE_EQUAL;
105
    if ((aInt & bInt) >= 0) {
106
        if (aInt < bInt) return GE_LESS;
107
        else if (aInt == bInt) return GE_EQUAL;
108
        else return GE_GREATER;
109
    } else {
110
        if (aInt > bInt) return GE_LESS;
111
        else if (aInt == bInt) return GE_EQUAL;
112
        else return GE_GREATER;
113
    }
114
}
115
116
ARM_EABI_FNALIAS(fcmpun, unordsf2)
117
118
COMPILER_RT_ABI int
119
__unordsf2(fp_t a, fp_t b) {
120
    const rep_t aAbs = toRep(a) & absMask;
121
    const rep_t bAbs = toRep(b) & absMask;
122
    return aAbs > infRep || bAbs > infRep;
123
}
124
125
// The following are alternative names for the preceding routines.
126
127
COMPILER_RT_ABI enum LE_RESULT
128
__eqsf2(fp_t a, fp_t b) {
129
    return __lesf2(a, b);
130
}
131
132
COMPILER_RT_ABI enum LE_RESULT
133
__ltsf2(fp_t a, fp_t b) {
134
    return __lesf2(a, b);
135
}
136
137
COMPILER_RT_ABI enum LE_RESULT
138
__nesf2(fp_t a, fp_t b) {
139
    return __lesf2(a, b);
140
}
141
142
COMPILER_RT_ABI enum GE_RESULT
143
__gtsf2(fp_t a, fp_t b) {
144
    return __gesf2(a, b);
145
}