]> git.proxmox.com Git - ceph.git/blame - ceph/src/boost/libs/gil/test/core/promote_integral.cpp
import quincy beta 17.1.0
[ceph.git] / ceph / src / boost / libs / gil / test / core / promote_integral.cpp
CommitLineData
92f5a8d4
TL
1// Boost.GIL (Generic Image Library)
2//
3// Copyright (c) 2015, Oracle and/or its affiliates.
4// Contributed and/or modified by Menelaos Karavelas, on behalf of Oracle
5//
6// Licensed under the Boost Software License version 1.0.
7// http://www.boost.org/users/license.html
8//
9// Source: Boost.Geometry (aka GGL, Generic Geometry Library)
10// Modifications: adapted for Boost.GIL
11// - Rename namespace boost::geometry to boost::gil
12// - Rename define BOOST_GEOMETRY_TEST_DEBUG to BOOST_GIL_TEST_DEBUG
13// - Remove use of macro BOOST_GEOMETRY_CONDITION
14// - Remove support for boost::multiprecision types
15// - Remove support for 128-bit integer types
16// - Update and sort includes
17// - Add explicit conversions to avoid warnings due to implicit integral promotions
18//
19// Uncomment to enable debugging output
20//#define BOOST_GIL_TEST_DEBUG 1
f67539c2 21#include <boost/config.hpp> // BOOST_HAS_LONG_LONG
92f5a8d4
TL
22#include <boost/gil/promote_integral.hpp>
23
f67539c2
TL
24#include <boost/core/lightweight_test.hpp>
25
92f5a8d4
TL
26#include <algorithm>
27#include <climits>
28#include <cstddef>
29#ifdef BOOST_GIL_TEST_DEBUG
30#include <iostream>
31#endif
32#include <limits>
33#include <string>
34
92f5a8d4
TL
35namespace bg = boost::gil;
36
37template
38<
39 typename T,
40 bool Signed = std::is_fundamental<T>::value && !std::is_unsigned<T>::type::value
41>
42struct absolute_value
43{
44 static inline T apply(T const& t)
45 {
46 return static_cast<T>(t < 0 ? -t : t);
47 }
48};
49
50template <typename T>
51struct absolute_value<T, false>
52{
53 static inline T apply(T const& t)
54 {
55 return t;
56 }
57};
58
59template
60 <
61 typename Integral,
62 typename Promoted,
63 bool Signed = !std::is_unsigned<Promoted>::value
64 >
65struct test_max_values
66{
67 static inline void apply()
68 {
69 // Use >= where value is guaranteed to never be greater than comparator
70 // but to avoid warning: comparing floating point with == is unsafe.
71
72 Promoted min_value = (std::numeric_limits<Integral>::min)();
73 // Explicit casts to avoid warning: conversion to short int from int may alter its value
74 min_value = static_cast<Promoted>(min_value * min_value);
f67539c2
TL
75 BOOST_TEST(absolute_value<Promoted>::apply(min_value) >= min_value);
76 BOOST_TEST(absolute_value<Promoted>::apply(min_value) <= min_value);
92f5a8d4
TL
77 Promoted max_value = (std::numeric_limits<Integral>::max)();
78 max_value = static_cast<Promoted>(max_value * max_value);
f67539c2
TL
79 BOOST_TEST(absolute_value<Promoted>::apply(max_value) >= max_value);
80 BOOST_TEST(absolute_value<Promoted>::apply(max_value) <= max_value);
92f5a8d4
TL
81
82#ifdef BOOST_GIL_TEST_DEBUG
83 std::cout << "integral min_value^2: " << min_value << std::endl;
84 std::cout << "promoted max_value: "
85 << (std::numeric_limits<Promoted>::max)() << std::endl;
86#endif
87 }
88};
89
90template <typename Integral, typename Promoted>
91struct test_max_values<Integral, Promoted, false>
92{
93 static inline void apply()
94 {
95 Promoted max_value = (std::numeric_limits<Integral>::max)();
96 Promoted max_value_sqr = static_cast<Promoted>(max_value * max_value);
f67539c2 97 BOOST_TEST(max_value_sqr < (std::numeric_limits<Promoted>::max)()
92f5a8d4
TL
98 &&
99 max_value_sqr > max_value);
100
101#ifdef BOOST_GIL_TEST_DEBUG
102 std::cout << "integral max_value^2: " << max_value_sqr << std::endl;
103 std::cout << "promoted max_value: "
104 << (std::numeric_limits<Promoted>::max)() << std::endl;
105#endif
106 }
107};
108
109
110// helper function that returns the bit size of a type
111template
112 <
113 typename T,
114 bool IsFundamental = std::is_fundamental<T>::value
115 >
116struct bit_size_impl : std::integral_constant<std::size_t, 0>
117{};
118
119template <typename T>
120struct bit_size_impl<T, true> : bg::detail::promote_integral::bit_size<T>::type
121{};
122
123template <typename T>
124std::size_t bit_size()
125{
126 return bit_size_impl<T>::value;
127}
128
f67539c2
TL
129#define BOOST_CHECK_MESSAGE(expr, msg) BOOST_TEST(expr)
130
92f5a8d4
TL
131template <bool PromoteUnsignedToUnsigned>
132struct test_promote_integral
133{
134 template <typename Type, typename ExpectedPromotedType>
135 static inline void apply(std::string const& case_id)
136 {
137 using promoted_integral_type = typename bg::promote_integral
138 <
139 Type, PromoteUnsignedToUnsigned
140 >::type;
141
142 bool const same_types = std::is_same
143 <
144 promoted_integral_type, ExpectedPromotedType
145 >::value;
146
147 BOOST_CHECK_MESSAGE(same_types,
148 "case ID: " << case_id
149 << "input type: " << typeid(Type).name()
150 << "; detected: "
151 << typeid(promoted_integral_type).name()
152 << "; expected: "
153 << typeid(ExpectedPromotedType).name());
154
155 if (!std::is_same<Type, promoted_integral_type>::value)
156 {
157 test_max_values<Type, promoted_integral_type>::apply();
158 }
159
160#ifdef BOOST_GIL_TEST_DEBUG
161 std::cout << "case ID: " << case_id << std::endl
162 << "type : " << typeid(Type).name()
163 << ", sizeof (bits): " << bit_size<Type>()
164 << ", min value: "
165 << (std::numeric_limits<Type>::min)()
166 << ", max value: "
167 << (std::numeric_limits<Type>::max)()
168 << std::endl;
169 std::cout << "detected promoted type : "
170 << typeid(promoted_integral_type).name()
171 << ", sizeof (bits): " << bit_size<promoted_integral_type>()
172 << ", min value: "
173 << (std::numeric_limits<promoted_integral_type>::min)()
174 << ", max value: "
175 << (std::numeric_limits<promoted_integral_type>::max)()
176 << std::endl;
177 std::cout << "expected promoted type : "
178 << typeid(ExpectedPromotedType).name()
179 << ", sizeof (bits): " << bit_size<ExpectedPromotedType>()
180 << ", min value: "
181 << (std::numeric_limits<ExpectedPromotedType>::min)()
182 << ", max value: "
183 << (std::numeric_limits<ExpectedPromotedType>::max)()
184 << std::endl;
185 std::cout << std::endl;
186#endif
187 }
188};
189
190template
191 <
192 typename T,
193 bool PromoteUnsignedToUnsigned = false,
194 bool IsSigned = !std::is_unsigned<T>::value
195 >
196struct test_promotion
197{
198 static inline void apply(std::string case_id)
199 {
200#ifdef BOOST_GIL_TEST_DEBUG
201 std::cout << "*** "
202 << (IsSigned ? "signed" : "unsigned")
203 << " -> signed ***" << std::endl;
204#endif
205
206 using tester = test_promote_integral<PromoteUnsignedToUnsigned>;
207
208 case_id += (PromoteUnsignedToUnsigned ? "-t" : "-f");
209
210 std::size_t min_size = 2 * bit_size<T>() - 1;
211 if (!IsSigned)
212 {
213 min_size += 2;
214 }
215
216#ifdef BOOST_GIL_TEST_DEBUG
217 std::cout << "min size: " << min_size << std::endl;
218#endif
219
220 if (bit_size<short>() >= min_size)
221 {
222 tester::template apply<T, short>(case_id);
223 }
224 else if (bit_size<int>() >= min_size)
225 {
226 tester::template apply<T, int>(case_id);
227 }
228 else if (bit_size<long>() >= min_size)
229 {
230 tester::template apply<T, long>(case_id);
231 }
232#if defined(BOOST_HAS_LONG_LONG)
233 else if (bit_size<boost::long_long_type>() >= min_size)
234 {
235 tester::template apply<T, boost::long_long_type>(case_id);
236 }
237#endif
238 else
239 {
240 tester::template apply<T, T>(case_id);
241 }
242 }
243};
244
245template <typename T>
246struct test_promotion<T, true, false>
247{
248 static inline void apply(std::string case_id)
249 {
250#ifdef BOOST_GIL_TEST_DEBUG
251 std::cout << "*** unsigned -> unsigned ***" << std::endl;
252#endif
253 case_id += "-t";
254
255 using tester = test_promote_integral<true>;
256
257 std::size_t min_size = 2 * bit_size<T>();
258
259#ifdef BOOST_GIL_TEST_DEBUG
260 std::cout << "min size: " << min_size << std::endl;
261#endif
262
263 if (bit_size<unsigned short>() >= min_size)
264 {
265 tester::apply<T, unsigned short>(case_id);
266 }
267 else if (bit_size<unsigned int>() >= min_size)
268 {
269 tester::apply<T, unsigned int>(case_id);
270 }
271 else if (bit_size<unsigned long>() >= min_size)
272 {
273 tester::apply<T, unsigned long>(case_id);
274 }
275 else if (bit_size<std::size_t>() >= min_size)
276 {
277 tester::apply<T, std::size_t>(case_id);
278 }
279#if defined(BOOST_HAS_LONG_LONG)
280 else if (bit_size<boost::ulong_long_type>() >= min_size)
281 {
282 tester::template apply<T, boost::ulong_long_type>(case_id);
283 }
284#endif
285 else
286 {
287 tester::apply<T, T>(case_id);
288 }
289 }
290};
291
f67539c2 292void test_char()
92f5a8d4
TL
293{
294 test_promotion<char>::apply("char");
295 test_promotion<char, true>::apply("char");
296 test_promotion<signed char>::apply("schar");
297 test_promotion<signed char, true>::apply("schar");
298 test_promotion<unsigned char>::apply("uchar");
299 test_promotion<unsigned char, true>::apply("uchar");
300}
301
f67539c2 302void test_short()
92f5a8d4
TL
303{
304 test_promotion<short>::apply("short");
305 test_promotion<short, true>::apply("short");
306 test_promotion<unsigned short>::apply("ushort");
307 test_promotion<unsigned short, true>::apply("ushort");
308}
309
f67539c2 310void test_int()
92f5a8d4
TL
311{
312 test_promotion<int>::apply("int");
313 test_promotion<int, true>::apply("int");
314 test_promotion<unsigned int>::apply("uint");
315 test_promotion<unsigned int, true>::apply("uint");
316}
317
f67539c2 318void test_long()
92f5a8d4
TL
319{
320 test_promotion<long>::apply("long");
321 test_promotion<long, true>::apply("long");
322 test_promotion<unsigned long>::apply("ulong");
323 test_promotion<unsigned long, true>::apply("ulong");
324}
325
f67539c2 326void test_std_size_t()
92f5a8d4
TL
327{
328 test_promotion<std::size_t>::apply("size_t");
329 test_promotion<std::size_t, true>::apply("size_t");
330}
331
332#ifdef BOOST_HAS_LONG_LONG
f67539c2 333void test_long_long()
92f5a8d4
TL
334{
335 test_promotion<boost::long_long_type>::apply("long long");
336 test_promotion<boost::long_long_type, true>::apply("long long");
337 test_promotion<boost::ulong_long_type>::apply("ulong long");
338 test_promotion<boost::ulong_long_type, true>::apply("ulong long");
339}
340#endif
341
f67539c2 342void test_floating_point()
92f5a8d4
TL
343{
344 using tester1 = test_promote_integral<true>;
345 using tester2 = test_promote_integral<false>;
346
347 // for floating-point types we do not do any promotion
348 tester1::apply<float, float>("fp-f");
349 tester1::apply<double, double>("fp-d");
350 tester1::apply<long double, long double>("fp-ld");
351
352 tester2::apply<float, float>("fp-f");
353 tester2::apply<double, double>("fp-d");
354 tester2::apply<long double, long double>("fp-ld");
355}
f67539c2
TL
356
357int main()
358{
359 test_char();
360 test_short();
361 test_int();
362 test_long();
363 test_std_size_t();
364#ifdef BOOST_HAS_LONG_LONG
365 test_long_long();
366#endif
367 test_floating_point();
368
369 return boost::report_errors();
370}