1 /* C integers info.
2    Copyright (C) 2001-2010 Roberto Bagnara <bagnara@cs.unipr.it>
3    Copyright (C) 2010-2016 BUGSENG srl (http://bugseng.com)
4 
5 This file is part of the Parma Polyhedra Library (PPL).
6 
7 The PPL is free software; you can redistribute it and/or modify it
8 under the terms of the GNU General Public License as published by the
9 Free Software Foundation; either version 3 of the License, or (at your
10 option) any later version.
11 
12 The PPL is distributed in the hope that it will be useful, but WITHOUT
13 ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
14 FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
15 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 Foundation,
19 Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02111-1307, USA.
20 
21 For the most up-to-date information see the Parma Polyhedra Library
22 site: http://bugseng.com/products/ppl/ . */
23 
24 #ifndef PPL_C_Integer_hh
25 #define PPL_C_Integer_hh 1
26 
27 #include "meta_programming.hh"
28 #include <climits>
29 
30 // C99 defines LLONG_MIN, LLONG_MAX and ULLONG_MAX, but this part of
31 // C99 is not yet included into the C++ standard.
32 // GCC defines LONG_LONG_MIN, LONG_LONG_MAX and ULONG_LONG_MAX.
33 // Some compilers (such as Comeau C++ up to and including version 4.3.3)
34 // define nothing.  In this last case we make a reasonable guess.
35 #ifndef LLONG_MIN
36 #if defined(LONG_LONG_MIN)
37 #define LLONG_MIN LONG_LONG_MIN
38 #elif PPL_SIZEOF_LONG_LONG == 8
39 #define LLONG_MIN 0x8000000000000000LL
40 #endif
41 #endif
42 
43 #ifndef LLONG_MAX
44 #if defined(LONG_LONG_MAX)
45 #define LLONG_MAX LONG_LONG_MAX
46 #elif PPL_SIZEOF_LONG_LONG == 8
47 #define LLONG_MAX 0x7fffffffffffffffLL
48 #endif
49 #endif
50 
51 #ifndef ULLONG_MAX
52 #if defined(ULONG_LONG_MAX)
53 #define ULLONG_MAX ULONG_LONG_MAX
54 #elif PPL_SIZEOF_LONG_LONG == 8
55 #define ULLONG_MAX 0xffffffffffffffffULL
56 #endif
57 #endif
58 
59 namespace Parma_Polyhedra_Library {
60 
61 template <typename T>
62 struct C_Integer : public False { };
63 
64 template <>
65 struct C_Integer<char> : public True {
66   enum const_bool_value {
67 #if PPL_CXX_PLAIN_CHAR_IS_SIGNED
68     is_signed = true
69 #else
70     is_signed = false
71 #endif
72   };
73   typedef void smaller_type;
74   typedef void smaller_signed_type;
75   typedef void smaller_unsigned_type;
76 #if PPL_CXX_PLAIN_CHAR_IS_SIGNED
77   typedef unsigned char other_type;
78 #else
79   typedef signed char other_type;
80 #endif
81   static const char min = static_cast<char>(CHAR_MIN);
82   static const char max = static_cast<char>(CHAR_MAX);
83 };
84 
85 template <>
86 struct C_Integer<signed char> : public True {
87   enum const_bool_value {
88     is_signed = true
89   };
90   typedef void smaller_type;
91   typedef void smaller_signed_type;
92   typedef void smaller_unsigned_type;
93   typedef unsigned char other_type;
94   static const signed char min = static_cast<signed char>(SCHAR_MIN);
95   static const signed char max = static_cast<signed char>(SCHAR_MAX);
96 };
97 
98 template <>
99 struct C_Integer<signed short> : public True {
100   enum const_bool_value {
101     is_signed = true
102   };
103   typedef signed char smaller_type;
104   typedef signed char smaller_signed_type;
105   typedef unsigned char smaller_unsigned_type;
106   typedef unsigned short other_type;
107   static const signed short min = static_cast<signed short>(SHRT_MIN);
108   static const signed short max = static_cast<signed short>(SHRT_MAX);
109 };
110 
111 template <>
112 struct C_Integer<signed int> : public True {
113   enum const_bool_value {
114     is_signed = true
115   };
116   typedef signed short smaller_type;
117   typedef signed short smaller_signed_type;
118   typedef unsigned short smaller_unsigned_type;
119   typedef unsigned int other_type;
120   static const signed int min = INT_MIN;
121   static const signed int max = INT_MAX;
122 };
123 
124 template <>
125 struct C_Integer<signed long> : public True {
126   enum const_bool_value {
127     is_signed = true
128   };
129   typedef signed int smaller_type;
130   typedef signed int smaller_signed_type;
131   typedef unsigned int smaller_unsigned_type;
132   typedef unsigned long other_type;
133   static const signed long min = LONG_MIN;
134   static const signed long max = LONG_MAX;
135 };
136 
137 template <>
138 struct C_Integer<signed long long> : public True {
139   enum const_bool_value {
140     is_signed = true
141   };
142   typedef signed long smaller_type;
143   typedef signed long smaller_signed_type;
144   typedef unsigned long smaller_unsigned_type;
145   typedef unsigned long long other_type;
146   static const signed long long min = LLONG_MIN;
147   static const signed long long max = LLONG_MAX;
148 };
149 
150 template <>
151 struct C_Integer<unsigned char> : public True {
152   enum const_bool_value {
153     is_signed = false
154   };
155   typedef void smaller_type;
156   typedef void smaller_signed_type;
157   typedef void smaller_unsigned_type;
158   typedef signed char other_type;
159   static const unsigned char min = static_cast<unsigned char>(0U);
160   static const unsigned char max = static_cast<unsigned char>(UCHAR_MAX);
161 };
162 
163 template <>
164 struct C_Integer<unsigned short> : public True {
165   enum const_bool_value {
166     is_signed = false
167   };
168   typedef unsigned char smaller_type;
169   typedef signed char smaller_signed_type;
170   typedef unsigned char smaller_unsigned_type;
171   typedef signed short other_type;
172   static const unsigned short min = static_cast<unsigned short>(0U);
173   static const unsigned short max = static_cast<unsigned short>(USHRT_MAX);
174 };
175 
176 template <>
177 struct C_Integer<unsigned int> : public True {
178   enum const_bool_value {
179     is_signed = false
180   };
181   typedef unsigned short smaller_type;
182   typedef signed short smaller_signed_type;
183   typedef unsigned short smaller_unsigned_type;
184   typedef signed int other_type;
185   static const unsigned int min = 0U;
186   static const unsigned int max = UINT_MAX;
187 };
188 
189 template <>
190 struct C_Integer<unsigned long> : public True {
191   enum const_bool_value {
192     is_signed = false
193   };
194   typedef unsigned int smaller_type;
195   typedef signed int smaller_signed_type;
196   typedef unsigned int smaller_unsigned_type;
197   typedef signed long other_type;
198   static const unsigned long min = 0UL;
199   static const unsigned long max = ULONG_MAX;
200 };
201 
202 template <>
203 struct C_Integer<unsigned long long> : public True {
204   enum const_bool_value {
205     is_signed = false
206   };
207   typedef unsigned long smaller_type;
208   typedef signed long smaller_signed_type;
209   typedef unsigned long smaller_unsigned_type;
210   typedef signed long long other_type;
211   static const unsigned long long min = 0ULL;
212   static const unsigned long long max = ULLONG_MAX;
213 };
214 
215 } // namespace Parma_Polyhedra_Library
216 
217 #endif // !defined(PPL_C_Integer_hh)
218