1
1
// FIXME(integers): add tests that perform the same checks in generic code
2
2
3
3
%{
4
- import gyb
4
+ from SwiftIntTypes import all_integer_types, int_max, int_min
5
+ from SwiftFloatingPointTypes import all_floating_point_types, getFtoIBounds
6
+
7
+ from decimal import Decimal
5
8
}%
6
9
7
10
import StdlibUnittest
@@ -34,22 +37,15 @@ func getTooLargeMessage() -> String {
34
37
return ""
35
38
}
36
39
37
- %{
38
-
39
- int_to_int_conversion_template = gyb.parse_template("int_to_int_conversion",
40
- """
41
- %{
42
- from SwiftIntTypes import all_integer_types, int_max, int_min
43
- from SwiftFloatingPointTypes import all_floating_point_types
44
-
45
- }%
40
+ % word_bits = int(target_ptrsize)
46
41
% for self_ty in all_integer_types(word_bits):
47
42
% selfBits = self_ty.bits
48
43
% selfSigned = self_ty.is_signed
49
44
% selfMin = self_ty.min
50
45
% selfMax = self_ty.max
51
46
% Self = self_ty.stdlib_name
52
47
48
+ % # Test conversion behaviors for all integer types
53
49
% for other_ty in all_integer_types(word_bits):
54
50
% otherBits = other_ty.bits
55
51
% otherSigned = other_ty.is_signed
@@ -60,9 +56,10 @@ from SwiftFloatingPointTypes import all_floating_point_types
60
56
% for testValue in [selfMin, selfMax, selfMin - 1, selfMax + 1, otherMin, otherMax]:
61
57
62
58
% if testValue < otherMin or testValue > otherMax:
63
- % # Can't construct `other` value, do nothing and continue.
64
-
59
+ % # Can't construct `other` value, do nothing and continue.
60
+ % pass
65
61
% elif testValue >= selfMin and testValue <= selfMax:
62
+ % # Test value can be represented by Self, test conversion succeeds
66
63
67
64
/// Always-safe conversion from ${Other}(${testValue}) to ${Self}.
68
65
FixedPointConversionTraps.test("${Other}To${Self}Conversion/dest=${testValue}") {
@@ -75,18 +72,19 @@ FixedPointConversionTraps.test("${Other}To${Self}Conversion/dest=${testValue}")
75
72
FixedPointConversionFailure.test("${Other}To${Self}FailableConversion/dest=${testValue}") {
76
73
// Test that nothing interesting happens and we end up with a non-nil, identical result.
77
74
let input = get${Other}(${testValue})
78
- var result = ${Self}(exactly: input)
75
+ let result = ${Self}(exactly: input)
79
76
expectEqual(${testValue}, result)
80
77
}
81
78
82
79
% else:
80
+ % # Test value is out of range of Self, test conversion fails
83
81
84
82
/// Always-failing conversion from ${Other}(${testValue}) to ${Self}.
85
83
FixedPointConversionTraps.test("${Other}To${Self}Conversion/dest=${testValue}") {
86
84
// Test that we check if we fail and crash when an integer would be truncated in conversion.
87
85
let input = get${Other}(${testValue})
88
86
expectCrashLater()
89
- var result = ${Self}(input)
87
+ let result = ${Self}(input)
90
88
_blackHole(result)
91
89
}
92
90
@@ -96,60 +94,78 @@ FixedPointConversionFailure.test("${Other}To${Self}Conversion/dest=${testValue}"
96
94
let input = get${Other}(${testValue})
97
95
expectNil(${Self}(exactly: input))
98
96
}
99
- % end
100
97
98
+ % end
101
99
% end # for testValue in ...
102
100
% end # for in all_integer_types (Other)
103
101
102
+ % # Test conversion behaviors for all floating-point types
104
103
% for other_type in all_floating_point_types():
105
104
% Other = "Float" + str(other_type.bits)
106
105
% otherMin = -int_max(bits=other_type.explicit_significand_bits, signed=False)
107
106
% otherMax = int_max(bits=other_type.explicit_significand_bits, signed=False)
107
+ % (selfFtoIMin, selfFtoIMax) = getFtoIBounds(other_type.bits, selfBits, selfSigned)
108
108
109
109
% if Other == 'Float80':
110
110
#if !os(Windows) && (arch(i386) || arch(x86_64))
111
111
% end
112
112
113
- % for testValue in [repr(value) for value in [selfMin, selfMax, selfMin - 0.1, selfMax + 0.1, otherMin, otherMax, 0.0, -0.0, 0.1, -0.1]]:
113
+ % testValues = [
114
+ % Decimal(selfMin),
115
+ % Decimal(selfMax),
116
+ % Decimal(selfFtoIMin) - Decimal('0.1'),
117
+ % Decimal(selfFtoIMax) + Decimal('0.1'),
118
+ % Decimal(otherMin),
119
+ % Decimal(otherMax),
120
+ % Decimal('0.0'),
121
+ % Decimal('-0.0'),
122
+ % Decimal('0.1'),
123
+ % Decimal('-0.1')
124
+ % ]
125
+ % for testValue in testValues:
126
+ % testValueStr = str(testValue)
114
127
115
128
% if testValue < otherMin or testValue > otherMax:
116
129
% # Can't construct `other` value to test from, do nothing and continue.
130
+ % pass
131
+ % elif testValue >= selfFtoIMin and testValue <= selfFtoIMax and (testValue % 1).is_zero():
132
+ % # Test value can be represented exactly by Self, test two-way conversion
117
133
118
- % elif testValue >= selfMin and testValue <= selfMax and testValue % 1 == 0 and testValue != -0.0:
119
-
120
- FloatingPointConversionTruncations.test("${Other}To${Self}Conversion/dest=${testValue}") {
121
- let input = get${Other}(${testValue})
134
+ FloatingPointConversionTruncations.test("${Other}To${Self}Conversion/dest=${testValueStr}") {
135
+ let input = get${Other}(${testValueStr})
122
136
let result = ${Self}(input)
123
- var resultConvertedBack = ${Other}(result)
124
- expectEqual(${testValue }, resultConvertedBack)
137
+ let resultConvertedBack = ${Other}(result)
138
+ expectEqual(${testValueStr }, resultConvertedBack)
125
139
}
126
140
127
- FloatingPointConversionFailures.test("${Other}To${Self}FailableConversion/dest=${testValue }") {
128
- let input = get${Other}(${testValue })
129
- expectNil (${Self}(exactly: input))
141
+ FloatingPointConversionFailures.test("${Other}To${Self}FailableConversion/dest=${testValueStr }") {
142
+ let input = get${Other}(${testValueStr })
143
+ expectNotNil (${Self}(exactly: input))
130
144
}
131
145
132
146
% else:
133
-
134
- % if testValue > selfMax:
135
- FloatingPointConversionTraps.test("${Other}To${Self}Conversion/dest=${testValue }")
147
+ % if testValue > selfFtoIMax:
148
+ % # Test value exceeds maximum value of Self, test for too large message
149
+ FloatingPointConversionTraps.test("${Other}To${Self}Conversion/dest=${testValueStr }")
136
150
.crashOutputMatches(getTooLargeMessage()).code {
137
151
expectCrashLater()
138
- % elif testValue < selfMin:
139
- FloatingPointConversionTraps.test("${Other}To${Self}Conversion/dest=${testValue}")
152
+ % elif testValue < selfFtoIMin:
153
+ % # Test value doesn't reach minimum value of Self, test for too small message
154
+ FloatingPointConversionTraps.test("${Other}To${Self}Conversion/dest=${testValueStr}")
140
155
.crashOutputMatches(getTooSmallMessage()).code {
141
156
expectCrashLater()
142
157
% else:
143
- FloatingPointConversionTruncations.test("${Other}To${Self}Conversion/dest=${testValue}") {
158
+ % # Test value can be represented inexactly by Self, test for truncation
159
+ FloatingPointConversionTruncations.test("${Other}To${Self}Conversion/dest=${testValueStr}") {
144
160
% end
145
- let input = get${Other}(${testValue })
146
- var result = ${Self}(input)
147
- var resultConvertedBack = ${Other}(result)
161
+ let input = get${Other}(${testValueStr })
162
+ let result = ${Self}(input)
163
+ let resultConvertedBack = ${Other}(result)
148
164
expectNotEqual(input, resultConvertedBack)
149
165
}
150
166
151
- FloatingPointConversionFailures.test("${Other}To${Self}Conversion/dest=${testValue }") {
152
- let input = get${Other}(${testValue })
167
+ FloatingPointConversionFailures.test("${Other}To${Self}Conversion/dest=${testValueStr }") {
168
+ let input = get${Other}(${testValueStr })
153
169
expectNil(${Self}(exactly: input))
154
170
}
155
171
% end
@@ -208,26 +224,4 @@ FloatingPointConversionFailures.test("${Self}/${Other}/NaN") {
208
224
% end # for in all_floating_point_types (Other)
209
225
% end # for in all_integer_types (Self)
210
226
211
- """)
212
-
213
- }%
214
-
215
- #if arch(i386) || arch(arm)
216
-
217
- ${gyb.execute_template(
218
- int_to_int_conversion_template,
219
- word_bits=32)}
220
-
221
- #elseif arch(x86_64) || arch(arm64) || arch(powerpc64) || arch(powerpc64le) || arch(s390x)
222
-
223
- ${gyb.execute_template(
224
- int_to_int_conversion_template,
225
- word_bits=64)}
226
-
227
- #else
228
-
229
- _UnimplementedError()
230
-
231
- #endif
232
-
233
227
runAllTests()
0 commit comments