Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(748)

Side by Side Diff: webrtc/base/safe_minmax.h

Issue 2802423002: Rename safe_cmp::{Eq,Ne,Lt,Le,Ge,Gt} to Safe{Eq,Ne,Lt,Le,Ge,Gt} (Closed)
Patch Set: Created 3 years, 6 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch
« no previous file with comments | « webrtc/base/safe_compare_unittest.cc ('k') | no next file » | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 /* 1 /*
2 * Copyright 2017 The WebRTC Project Authors. All rights reserved. 2 * Copyright 2017 The WebRTC Project Authors. All rights reserved.
3 * 3 *
4 * Use of this source code is governed by a BSD-style license 4 * Use of this source code is governed by a BSD-style license
5 * that can be found in the LICENSE file in the root of the source 5 * that can be found in the LICENSE file in the root of the source
6 * tree. An additional intellectual property rights grant can be found 6 * tree. An additional intellectual property rights grant can be found
7 * in the file PATENTS. All contributing project authors may 7 * in the file PATENTS. All contributing project authors may
8 * be found in the AUTHORS file in the root of the source tree. 8 * be found in the AUTHORS file in the root of the source tree.
9 */ 9 */
10 10
(...skipping 124 matching lines...) Expand 10 before | Expand all | Expand 10 after
135 ""); 135 "");
136 }; 136 };
137 137
138 // Specialization for when both types are integral. 138 // Specialization for when both types are integral.
139 template <typename T1, typename T2> 139 template <typename T1, typename T2>
140 struct MType<T1, T2, true, true> { 140 struct MType<T1, T2, true, true> {
141 // The type with the lowest minimum value. In case of a tie, the type with 141 // The type with the lowest minimum value. In case of a tie, the type with
142 // the lowest maximum value. In case that too is a tie, the types have the 142 // the lowest maximum value. In case that too is a tie, the types have the
143 // same range, and we arbitrarily pick T1. 143 // same range, and we arbitrarily pick T1.
144 using min_t = typename std::conditional< 144 using min_t = typename std::conditional<
145 safe_cmp::Lt(Limits<T1>::lowest, Limits<T2>::lowest), 145 SafeLt(Limits<T1>::lowest, Limits<T2>::lowest),
146 T1, 146 T1,
147 typename std::conditional< 147 typename std::conditional<
148 safe_cmp::Gt(Limits<T1>::lowest, Limits<T2>::lowest), 148 SafeGt(Limits<T1>::lowest, Limits<T2>::lowest),
149 T2, 149 T2,
150 typename std::conditional<safe_cmp::Le(Limits<T1>::max, 150 typename std::conditional<SafeLe(Limits<T1>::max, Limits<T2>::max),
151 Limits<T2>::max),
152 T1, 151 T1,
153 T2>::type>::type>::type; 152 T2>::type>::type>::type;
154 static_assert(std::is_same<min_t, T1>::value || 153 static_assert(std::is_same<min_t, T1>::value ||
155 std::is_same<min_t, T2>::value, 154 std::is_same<min_t, T2>::value,
156 ""); 155 "");
157 156
158 // The type with the highest maximum value. In case of a tie, the types have 157 // The type with the highest maximum value. In case of a tie, the types have
159 // the same range (because in C++, integer types with the same maximum also 158 // the same range (because in C++, integer types with the same maximum also
160 // have the same minimum). 159 // have the same minimum).
161 static_assert(safe_cmp::Ne(Limits<T1>::max, Limits<T2>::max) || 160 static_assert(SafeNe(Limits<T1>::max, Limits<T2>::max) ||
162 safe_cmp::Eq(Limits<T1>::lowest, Limits<T2>::lowest), 161 SafeEq(Limits<T1>::lowest, Limits<T2>::lowest),
163 "integer types with the same max should have the same min"); 162 "integer types with the same max should have the same min");
164 using max_t = typename std:: 163 using max_t = typename std::
165 conditional<safe_cmp::Ge(Limits<T1>::max, Limits<T2>::max), T1, T2>::type; 164 conditional<SafeGe(Limits<T1>::max, Limits<T2>::max), T1, T2>::type;
166 static_assert(std::is_same<max_t, T1>::value || 165 static_assert(std::is_same<max_t, T1>::value ||
167 std::is_same<max_t, T2>::value, 166 std::is_same<max_t, T2>::value,
168 ""); 167 "");
169 }; 168 };
170 169
171 // A dummy type that we pass around at compile time but never actually use. 170 // A dummy type that we pass around at compile time but never actually use.
172 // Declared but not defined. 171 // Declared but not defined.
173 struct DefaultType; 172 struct DefaultType;
174 173
175 // ::type is A, except we fall back to B if A is DefaultType. We static_assert 174 // ::type is A, except we fall back to B if A is DefaultType. We static_assert
176 // that the chosen type can hold all values that B can hold. 175 // that the chosen type can hold all values that B can hold.
177 template <typename A, typename B> 176 template <typename A, typename B>
178 struct TypeOr { 177 struct TypeOr {
179 using type = typename std:: 178 using type = typename std::
180 conditional<std::is_same<A, DefaultType>::value, B, A>::type; 179 conditional<std::is_same<A, DefaultType>::value, B, A>::type;
181 static_assert(safe_cmp::Le(Limits<type>::lowest, Limits<B>::lowest) && 180 static_assert(SafeLe(Limits<type>::lowest, Limits<B>::lowest) &&
182 safe_cmp::Ge(Limits<type>::max, Limits<B>::max), 181 SafeGe(Limits<type>::max, Limits<B>::max),
183 "The specified type isn't large enough"); 182 "The specified type isn't large enough");
184 static_assert(IsIntlike<type>::value == IsIntlike<B>::value && 183 static_assert(IsIntlike<type>::value == IsIntlike<B>::value &&
185 std::is_floating_point<type>::value == 184 std::is_floating_point<type>::value ==
186 std::is_floating_point<type>::value, 185 std::is_floating_point<type>::value,
187 "float<->int conversions not allowed"); 186 "float<->int conversions not allowed");
188 }; 187 };
189 188
190 } // namespace safe_minmax_impl 189 } // namespace safe_minmax_impl
191 190
192 template < 191 template <
193 typename R = safe_minmax_impl::DefaultType, 192 typename R = safe_minmax_impl::DefaultType,
194 typename T1 = safe_minmax_impl::DefaultType, 193 typename T1 = safe_minmax_impl::DefaultType,
195 typename T2 = safe_minmax_impl::DefaultType, 194 typename T2 = safe_minmax_impl::DefaultType,
196 typename R2 = typename safe_minmax_impl::TypeOr< 195 typename R2 = typename safe_minmax_impl::TypeOr<
197 R, 196 R,
198 typename safe_minmax_impl::MType< 197 typename safe_minmax_impl::MType<
199 typename safe_minmax_impl::UnderlyingType<T1>::type, 198 typename safe_minmax_impl::UnderlyingType<T1>::type,
200 typename safe_minmax_impl::UnderlyingType<T2>::type>::min_t>::type> 199 typename safe_minmax_impl::UnderlyingType<T2>::type>::min_t>::type>
201 constexpr R2 SafeMin(T1 a, T2 b) { 200 constexpr R2 SafeMin(T1 a, T2 b) {
202 static_assert(IsIntlike<T1>::value || std::is_floating_point<T1>::value, 201 static_assert(IsIntlike<T1>::value || std::is_floating_point<T1>::value,
203 "The first argument must be integral or floating-point"); 202 "The first argument must be integral or floating-point");
204 static_assert(IsIntlike<T2>::value || std::is_floating_point<T2>::value, 203 static_assert(IsIntlike<T2>::value || std::is_floating_point<T2>::value,
205 "The second argument must be integral or floating-point"); 204 "The second argument must be integral or floating-point");
206 return safe_cmp::Lt(a, b) ? static_cast<R2>(a) : static_cast<R2>(b); 205 return SafeLt(a, b) ? static_cast<R2>(a) : static_cast<R2>(b);
207 } 206 }
208 207
209 template < 208 template <
210 typename R = safe_minmax_impl::DefaultType, 209 typename R = safe_minmax_impl::DefaultType,
211 typename T1 = safe_minmax_impl::DefaultType, 210 typename T1 = safe_minmax_impl::DefaultType,
212 typename T2 = safe_minmax_impl::DefaultType, 211 typename T2 = safe_minmax_impl::DefaultType,
213 typename R2 = typename safe_minmax_impl::TypeOr< 212 typename R2 = typename safe_minmax_impl::TypeOr<
214 R, 213 R,
215 typename safe_minmax_impl::MType< 214 typename safe_minmax_impl::MType<
216 typename safe_minmax_impl::UnderlyingType<T1>::type, 215 typename safe_minmax_impl::UnderlyingType<T1>::type,
217 typename safe_minmax_impl::UnderlyingType<T2>::type>::max_t>::type> 216 typename safe_minmax_impl::UnderlyingType<T2>::type>::max_t>::type>
218 constexpr R2 SafeMax(T1 a, T2 b) { 217 constexpr R2 SafeMax(T1 a, T2 b) {
219 static_assert(IsIntlike<T1>::value || std::is_floating_point<T1>::value, 218 static_assert(IsIntlike<T1>::value || std::is_floating_point<T1>::value,
220 "The first argument must be integral or floating-point"); 219 "The first argument must be integral or floating-point");
221 static_assert(IsIntlike<T2>::value || std::is_floating_point<T2>::value, 220 static_assert(IsIntlike<T2>::value || std::is_floating_point<T2>::value,
222 "The second argument must be integral or floating-point"); 221 "The second argument must be integral or floating-point");
223 return safe_cmp::Gt(a, b) ? static_cast<R2>(a) : static_cast<R2>(b); 222 return SafeGt(a, b) ? static_cast<R2>(a) : static_cast<R2>(b);
224 } 223 }
225 224
226 namespace safe_minmax_impl { 225 namespace safe_minmax_impl {
227 226
228 // Given three types T, L, and H, let ::type be a suitable return value for 227 // Given three types T, L, and H, let ::type be a suitable return value for
229 // SafeClamp(T, L, H). See the docs at the top of this file for details. 228 // SafeClamp(T, L, H). See the docs at the top of this file for details.
230 template <typename T, 229 template <typename T,
231 typename L, 230 typename L,
232 typename H, 231 typename H,
233 bool int1 = IsIntlike<T>::value, 232 bool int1 = IsIntlike<T>::value,
(...skipping 24 matching lines...) Expand all
258 // Is the given type an acceptable return type? (That is, can it represent 257 // Is the given type an acceptable return type? (That is, can it represent
259 // all possible return values, and is it no larger than the largest of the 258 // all possible return values, and is it no larger than the largest of the
260 // input types?) 259 // input types?)
261 template <typename A> 260 template <typename A>
262 struct AcceptableType { 261 struct AcceptableType {
263 private: 262 private:
264 static constexpr bool not_too_large = sizeof(A) <= sizeof(L) || 263 static constexpr bool not_too_large = sizeof(A) <= sizeof(L) ||
265 sizeof(A) <= sizeof(H) || 264 sizeof(A) <= sizeof(H) ||
266 sizeof(A) <= sizeof(T); 265 sizeof(A) <= sizeof(T);
267 static constexpr bool range_contained = 266 static constexpr bool range_contained =
268 safe_cmp::Le(Limits<A>::lowest, r_min) && 267 SafeLe(Limits<A>::lowest, r_min) && SafeLe(r_max, Limits<A>::max);
269 safe_cmp::Le(r_max, Limits<A>::max);
270 268
271 public: 269 public:
272 static constexpr bool value = not_too_large && range_contained; 270 static constexpr bool value = not_too_large && range_contained;
273 }; 271 };
274 272
275 using best_signed_type = typename std::conditional< 273 using best_signed_type = typename std::conditional<
276 AcceptableType<int8_t>::value, 274 AcceptableType<int8_t>::value,
277 int8_t, 275 int8_t,
278 typename std::conditional< 276 typename std::conditional<
279 AcceptableType<int16_t>::value, 277 AcceptableType<int16_t>::value,
(...skipping 40 matching lines...) Expand 10 before | Expand all | Expand 10 after
320 typename safe_minmax_impl::UnderlyingType<L>::type, 318 typename safe_minmax_impl::UnderlyingType<L>::type,
321 typename safe_minmax_impl::UnderlyingType<H>::type>::type>::type> 319 typename safe_minmax_impl::UnderlyingType<H>::type>::type>::type>
322 R2 SafeClamp(T x, L min, H max) { 320 R2 SafeClamp(T x, L min, H max) {
323 static_assert(IsIntlike<H>::value || std::is_floating_point<H>::value, 321 static_assert(IsIntlike<H>::value || std::is_floating_point<H>::value,
324 "The first argument must be integral or floating-point"); 322 "The first argument must be integral or floating-point");
325 static_assert(IsIntlike<T>::value || std::is_floating_point<T>::value, 323 static_assert(IsIntlike<T>::value || std::is_floating_point<T>::value,
326 "The second argument must be integral or floating-point"); 324 "The second argument must be integral or floating-point");
327 static_assert(IsIntlike<L>::value || std::is_floating_point<L>::value, 325 static_assert(IsIntlike<L>::value || std::is_floating_point<L>::value,
328 "The third argument must be integral or floating-point"); 326 "The third argument must be integral or floating-point");
329 RTC_DCHECK_LE(min, max); 327 RTC_DCHECK_LE(min, max);
330 return safe_cmp::Le(x, min) 328 return SafeLe(x, min)
331 ? static_cast<R2>(min) 329 ? static_cast<R2>(min)
332 : safe_cmp::Ge(x, max) ? static_cast<R2>(max) : static_cast<R2>(x); 330 : SafeGe(x, max) ? static_cast<R2>(max) : static_cast<R2>(x);
333 } 331 }
334 332
335 } // namespace rtc 333 } // namespace rtc
336 334
337 #endif // WEBRTC_BASE_SAFE_MINMAX_H_ 335 #endif // WEBRTC_BASE_SAFE_MINMAX_H_
OLDNEW
« no previous file with comments | « webrtc/base/safe_compare_unittest.cc ('k') | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698