1 #ifndef _DEINT32_H 2 #define _DEINT32_H 3 /*------------------------------------------------------------------------- 4 * drawElements Base Portability Library 5 * ------------------------------------- 6 * 7 * Copyright 2014 The Android Open Source Project 8 * 9 * Licensed under the Apache License, Version 2.0 (the "License"); 10 * you may not use this file except in compliance with the License. 11 * You may obtain a copy of the License at 12 * 13 * http://www.apache.org/licenses/LICENSE-2.0 14 * 15 * Unless required by applicable law or agreed to in writing, software 16 * distributed under the License is distributed on an "AS IS" BASIS, 17 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 18 * See the License for the specific language governing permissions and 19 * limitations under the License. 20 * 21 *//*! 22 * \file 23 * \brief 32-bit integer math. 24 *//*--------------------------------------------------------------------*/ 25 26 #include "deDefs.h" 27 28 #if (DE_COMPILER == DE_COMPILER_MSC) 29 # include <intrin.h> 30 #endif 31 32 DE_BEGIN_EXTERN_C 33 34 enum 35 { 36 DE_RCP_FRAC_BITS = 30 /*!< Number of fractional bits in deRcp32() result. */ 37 }; 38 39 void deRcp32 (deUint32 a, deUint32* rcp, int* exp); 40 void deInt32_computeLUTs (void); 41 void deInt32_selfTest (void); 42 43 /*--------------------------------------------------------------------*//*! 44 * \brief Compute the absolute of an int. 45 * \param a Input value. 46 * \return Absolute of the input value. 47 * 48 * \note The input 0x80000000u (for which the abs value cannot be 49 * represented), is asserted and returns the value itself. 50 *//*--------------------------------------------------------------------*/ 51 DE_INLINE int deAbs32 (int a) 52 { 53 DE_ASSERT((unsigned int) a != 0x80000000u); 54 return (a < 0) ? -a : a; 55 } 56 57 /*--------------------------------------------------------------------*//*! 58 * \brief Compute the signed minimum of two values. 59 * \param a First input value. 60 * \param b Second input value. 61 * \return The smallest of the two input values. 62 *//*--------------------------------------------------------------------*/ 63 DE_INLINE int deMin32 (int a, int b) 64 { 65 return (a <= b) ? a : b; 66 } 67 68 /*--------------------------------------------------------------------*//*! 69 * \brief Compute the signed maximum of two values. 70 * \param a First input value. 71 * \param b Second input value. 72 * \return The largest of the two input values. 73 *//*--------------------------------------------------------------------*/ 74 DE_INLINE int deMax32 (int a, int b) 75 { 76 return (a >= b) ? a : b; 77 } 78 79 /*--------------------------------------------------------------------*//*! 80 * \brief Compute the unsigned minimum of two values. 81 * \param a First input value. 82 * \param b Second input value. 83 * \return The smallest of the two input values. 84 *//*--------------------------------------------------------------------*/ 85 DE_INLINE deUint32 deMinu32 (deUint32 a, deUint32 b) 86 { 87 return (a <= b) ? a : b; 88 } 89 90 /*--------------------------------------------------------------------*//*! 91 * \brief Compute the unsigned maximum of two values. 92 * \param a First input value. 93 * \param b Second input value. 94 * \return The largest of the two input values. 95 *//*--------------------------------------------------------------------*/ 96 DE_INLINE deUint32 deMaxu32 (deUint32 a, deUint32 b) 97 { 98 return (a >= b) ? a : b; 99 } 100 101 /*--------------------------------------------------------------------*//*! 102 * \brief Check if a value is in the <b>inclusive<b> range [mn, mx]. 103 * \param a Value to check for range. 104 * \param mn Range minimum value. 105 * \param mx Range maximum value. 106 * \return True if (a >= mn) and (a <= mx), false otherwise. 107 * 108 * \see deInBounds32() 109 *//*--------------------------------------------------------------------*/ 110 DE_INLINE deBool deInRange32 (int a, int mn, int mx) 111 { 112 return (a >= mn) && (a <= mx); 113 } 114 115 /*--------------------------------------------------------------------*//*! 116 * \brief Check if a value is in the half-inclusive bounds [mn, mx[. 117 * \param a Value to check for range. 118 * \param mn Range minimum value. 119 * \param mx Range maximum value. 120 * \return True if (a >= mn) and (a < mx), false otherwise. 121 * 122 * \see deInRange32() 123 *//*--------------------------------------------------------------------*/ 124 DE_INLINE deBool deInBounds32 (int a, int mn, int mx) 125 { 126 return (a >= mn) && (a < mx); 127 } 128 129 /*--------------------------------------------------------------------*//*! 130 * \brief Clamp a value into the range [mn, mx]. 131 * \param a Value to clamp. 132 * \param mn Minimum value. 133 * \param mx Maximum value. 134 * \return The clamped value in [mn, mx] range. 135 *//*--------------------------------------------------------------------*/ 136 DE_INLINE int deClamp32 (int a, int mn, int mx) 137 { 138 DE_ASSERT(mn <= mx); 139 if (a < mn) return mn; 140 if (a > mx) return mx; 141 return a; 142 } 143 144 /*--------------------------------------------------------------------*//*! 145 * \brief Get the sign of an integer. 146 * \param a Input value. 147 * \return +1 if a>0, 0 if a==0, -1 if a<0. 148 *//*--------------------------------------------------------------------*/ 149 DE_INLINE int deSign32 (int a) 150 { 151 if (a > 0) return +1; 152 if (a < 0) return -1; 153 return 0; 154 } 155 156 /*--------------------------------------------------------------------*//*! 157 * \brief Extract the sign bit of a. 158 * \param a Input value. 159 * \return 0x80000000 if a<0, 0 otherwise. 160 *//*--------------------------------------------------------------------*/ 161 DE_INLINE deInt32 deSignBit32 (deInt32 a) 162 { 163 return (deInt32)((deUint32)a & 0x80000000u); 164 } 165 166 /*--------------------------------------------------------------------*//*! 167 * \brief Integer rotate right. 168 * \param val Value to rotate. 169 * \param r Number of bits to rotate (in range [0, 32]). 170 * \return The rotated value. 171 *//*--------------------------------------------------------------------*/ 172 DE_INLINE int deRor32 (int val, int r) 173 { 174 DE_ASSERT(r >= 0 && r <= 32); 175 if (r == 0 || r == 32) 176 return val; 177 else 178 return (int)(((deUint32)val >> r) | ((deUint32)val << (32-r))); 179 } 180 181 /*--------------------------------------------------------------------*//*! 182 * \brief Integer rotate left. 183 * \param val Value to rotate. 184 * \param r Number of bits to rotate (in range [0, 32]). 185 * \return The rotated value. 186 *//*--------------------------------------------------------------------*/ 187 DE_INLINE int deRol32 (int val, int r) 188 { 189 DE_ASSERT(r >= 0 && r <= 32); 190 if (r == 0 || r == 32) 191 return val; 192 else 193 return (int)(((deUint32)val << r) | ((deUint32)val >> (32-r))); 194 } 195 196 /*--------------------------------------------------------------------*//*! 197 * \brief Check if a value is a power-of-two. 198 * \param a Input value. 199 * \return True if input is a power-of-two value, false otherwise. 200 * 201 * \note Also returns true for zero. 202 *//*--------------------------------------------------------------------*/ 203 DE_INLINE deBool deIsPowerOfTwo32 (int a) 204 { 205 return ((a & (a - 1)) == 0); 206 } 207 208 /*--------------------------------------------------------------------*//*! 209 * \brief Check if a value is a power-of-two. 210 * \param a Input value. 211 * \return True if input is a power-of-two value, false otherwise. 212 * 213 * \note Also returns true for zero. 214 *//*--------------------------------------------------------------------*/ 215 DE_INLINE deBool deIsPowerOfTwo64 (deUint64 a) 216 { 217 return ((a & (a - 1ull)) == 0); 218 } 219 220 /*--------------------------------------------------------------------*//*! 221 * \brief Check if a value is a power-of-two. 222 * \param a Input value. 223 * \return True if input is a power-of-two value, false otherwise. 224 * 225 * \note Also returns true for zero. 226 *//*--------------------------------------------------------------------*/ 227 DE_INLINE deBool deIsPowerOfTwoSize (size_t a) 228 { 229 #if (DE_PTR_SIZE == 4) 230 return deIsPowerOfTwo32(a); 231 #elif (DE_PTR_SIZE == 8) 232 return deIsPowerOfTwo64(a); 233 #else 234 # error "Invalid DE_PTR_SIZE" 235 #endif 236 } 237 238 /*--------------------------------------------------------------------*//*! 239 * \brief Roud a value up to a power-of-two. 240 * \param a Input value. 241 * \return Smallest power-of-two value that is greater or equal to an input value. 242 *//*--------------------------------------------------------------------*/ 243 DE_INLINE deUint32 deSmallestGreaterOrEquallPowerOfTwoU32 (deUint32 a) 244 { 245 --a; 246 a |= a >> 1u; 247 a |= a >> 2u; 248 a |= a >> 4u; 249 a |= a >> 8u; 250 a |= a >> 16u; 251 return ++a; 252 } 253 254 /*--------------------------------------------------------------------*//*! 255 * \brief Roud a value up to a power-of-two. 256 * \param a Input value. 257 * \return Smallest power-of-two value that is greater or equal to an input value. 258 *//*--------------------------------------------------------------------*/ 259 DE_INLINE deUint64 deSmallestGreaterOrEquallPowerOfTwoU64 (deUint64 a) 260 { 261 --a; 262 a |= a >> 1u; 263 a |= a >> 2u; 264 a |= a >> 4u; 265 a |= a >> 8u; 266 a |= a >> 16u; 267 a |= a >> 32u; 268 return ++a; 269 } 270 271 /*--------------------------------------------------------------------*//*! 272 * \brief Roud a value up to a power-of-two. 273 * \param a Input value. 274 * \return Smallest power-of-two value that is greater or equal to an input value. 275 *//*--------------------------------------------------------------------*/ 276 DE_INLINE size_t deSmallestGreaterOrEquallPowerOfTwoSize (size_t a) 277 { 278 #if (DE_PTR_SIZE == 4) 279 return deSmallestGreaterOrEquallPowerOfTwoU32(a); 280 #elif (DE_PTR_SIZE == 8) 281 return deSmallestGreaterOrEquallPowerOfTwoU64(a); 282 #else 283 # error "Invalid DE_PTR_SIZE" 284 #endif 285 } 286 287 /*--------------------------------------------------------------------*//*! 288 * \brief Check if an integer is aligned to given power-of-two size. 289 * \param a Input value. 290 * \param align Alignment to check for. 291 * \return True if input is aligned, false otherwise. 292 *//*--------------------------------------------------------------------*/ 293 DE_INLINE deBool deIsAligned32 (int a, int align) 294 { 295 DE_ASSERT(deIsPowerOfTwo32(align)); 296 return ((a & (align-1)) == 0); 297 } 298 299 /*--------------------------------------------------------------------*//*! 300 * \brief Check if an integer is aligned to given power-of-two size. 301 * \param a Input value. 302 * \param align Alignment to check for. 303 * \return True if input is aligned, false otherwise. 304 *//*--------------------------------------------------------------------*/ 305 DE_INLINE deBool deIsAligned64 (deInt64 a, deInt64 align) 306 { 307 DE_ASSERT(deIsPowerOfTwo64(align)); 308 return ((a & (align-1)) == 0); 309 } 310 311 /*--------------------------------------------------------------------*//*! 312 * \brief Check if a pointer is aligned to given power-of-two size. 313 * \param ptr Input pointer. 314 * \param align Alignment to check for (power-of-two). 315 * \return True if input is aligned, false otherwise. 316 *//*--------------------------------------------------------------------*/ 317 DE_INLINE deBool deIsAlignedPtr (const void* ptr, deUintptr align) 318 { 319 DE_ASSERT((align & (align-1)) == 0); /* power of two */ 320 return (((deUintptr)ptr & (align-1)) == 0); 321 } 322 323 /*--------------------------------------------------------------------*//*! 324 * \brief Align an integer to given power-of-two size. 325 * \param val Input to align. 326 * \param align Alignment to check for (power-of-two). 327 * \return The aligned value (larger or equal to input). 328 *//*--------------------------------------------------------------------*/ 329 DE_INLINE deInt32 deAlign32 (deInt32 val, deInt32 align) 330 { 331 DE_ASSERT(deIsPowerOfTwo32(align)); 332 return (val + align - 1) & ~(align - 1); 333 } 334 335 /*--------------------------------------------------------------------*//*! 336 * \brief Align an integer to given power-of-two size. 337 * \param val Input to align. 338 * \param align Alignment to check for (power-of-two). 339 * \return The aligned value (larger or equal to input). 340 *//*--------------------------------------------------------------------*/ 341 DE_INLINE deInt64 deAlign64 (deInt64 val, deInt64 align) 342 { 343 DE_ASSERT(deIsPowerOfTwo64(align)); 344 return (val + align - 1) & ~(align - 1); 345 } 346 347 /*--------------------------------------------------------------------*//*! 348 * \brief Align a pointer to given power-of-two size. 349 * \param ptr Input pointer to align. 350 * \param align Alignment to check for (power-of-two). 351 * \return The aligned pointer (larger or equal to input). 352 *//*--------------------------------------------------------------------*/ 353 DE_INLINE void* deAlignPtr (void* ptr, deUintptr align) 354 { 355 deUintptr val = (deUintptr)ptr; 356 DE_ASSERT((align & (align-1)) == 0); /* power of two */ 357 return (void*)((val + align - 1) & ~(align - 1)); 358 } 359 360 /*--------------------------------------------------------------------*//*! 361 * \brief Align a size_t value to given power-of-two size. 362 * \param ptr Input value to align. 363 * \param align Alignment to check for (power-of-two). 364 * \return The aligned size (larger or equal to input). 365 *//*--------------------------------------------------------------------*/ 366 DE_INLINE size_t deAlignSize (size_t val, size_t align) 367 { 368 DE_ASSERT(deIsPowerOfTwoSize(align)); 369 return (val + align - 1) & ~(align - 1); 370 } 371 372 extern const deInt8 g_clzLUT[256]; 373 374 /*--------------------------------------------------------------------*//*! 375 * \brief Compute number of leading zeros in an integer. 376 * \param a Input value. 377 * \return The number of leading zero bits in the input. 378 *//*--------------------------------------------------------------------*/ 379 DE_INLINE int deClz32 (deUint32 a) 380 { 381 #if (DE_COMPILER == DE_COMPILER_MSC) 382 unsigned long i; 383 if (_BitScanReverse(&i, (unsigned long)a) == 0) 384 return 32; 385 else 386 return 31-i; 387 #elif (DE_COMPILER == DE_COMPILER_GCC) || (DE_COMPILER == DE_COMPILER_CLANG) 388 if (a == 0) 389 return 32; 390 else 391 return __builtin_clz((unsigned int)a); 392 #else 393 if ((a & 0xFF000000u) != 0) 394 return (int)g_clzLUT[a >> 24]; 395 if ((a & 0x00FF0000u) != 0) 396 return 8 + (int)g_clzLUT[a >> 16]; 397 if ((a & 0x0000FF00u) != 0) 398 return 16 + (int)g_clzLUT[a >> 8]; 399 return 24 + (int)g_clzLUT[a]; 400 #endif 401 } 402 403 extern const deInt8 g_ctzLUT[256]; 404 405 /*--------------------------------------------------------------------*//*! 406 * \brief Compute number of trailing zeros in an integer. 407 * \param a Input value. 408 * \return The number of trailing zero bits in the input. 409 *//*--------------------------------------------------------------------*/ 410 DE_INLINE int deCtz32 (deUint32 a) 411 { 412 #if (DE_COMPILER == DE_COMPILER_MSC) 413 unsigned long i; 414 if (_BitScanForward(&i, (unsigned long)a) == 0) 415 return 32; 416 else 417 return i; 418 #elif (DE_COMPILER == DE_COMPILER_GCC) || (DE_COMPILER == DE_COMPILER_CLANG) 419 if (a == 0) 420 return 32; 421 else 422 return __builtin_ctz((unsigned int)a); 423 #else 424 if ((a & 0x00FFFFFFu) == 0) 425 return (int)g_ctzLUT[a >> 24] + 24; 426 if ((a & 0x0000FFFFu) == 0) 427 return (int)g_ctzLUT[(a >> 16) & 0xffu] + 16; 428 if ((a & 0x000000FFu) == 0) 429 return (int)g_ctzLUT[(a >> 8) & 0xffu] + 8; 430 return (int)g_ctzLUT[a & 0xffu]; 431 #endif 432 } 433 434 /*--------------------------------------------------------------------*//*! 435 * \brief Compute integer 'floor' of 'log2' for a positive integer. 436 * \param a Input value. 437 * \return floor(log2(a)). 438 *//*--------------------------------------------------------------------*/ 439 DE_INLINE int deLog2Floor32 (deInt32 a) 440 { 441 DE_ASSERT(a > 0); 442 return 31 - deClz32((deUint32)a); 443 } 444 445 /*--------------------------------------------------------------------*//*! 446 * \brief Compute integer 'ceil' of 'log2' for a positive integer. 447 * \param a Input value. 448 * \return ceil(log2(a)). 449 *//*--------------------------------------------------------------------*/ 450 DE_INLINE int deLog2Ceil32 (deInt32 a) 451 { 452 int log2floor = deLog2Floor32(a); 453 if (deIsPowerOfTwo32(a)) 454 return log2floor; 455 else 456 return log2floor+1; 457 } 458 459 /*--------------------------------------------------------------------*//*! 460 * \brief Compute the bit population count of an integer. 461 * \param a Input value. 462 * \return The number of one bits in the input. 463 *//*--------------------------------------------------------------------*/ 464 DE_INLINE int dePop32 (deUint32 a) 465 { 466 deUint32 mask0 = 0x55555555; /* 1-bit values. */ 467 deUint32 mask1 = 0x33333333; /* 2-bit values. */ 468 deUint32 mask2 = 0x0f0f0f0f; /* 4-bit values. */ 469 deUint32 mask3 = 0x00ff00ff; /* 8-bit values. */ 470 deUint32 mask4 = 0x0000ffff; /* 16-bit values. */ 471 deUint32 t = (deUint32)a; 472 t = (t & mask0) + ((t>>1) & mask0); 473 t = (t & mask1) + ((t>>2) & mask1); 474 t = (t & mask2) + ((t>>4) & mask2); 475 t = (t & mask3) + ((t>>8) & mask3); 476 t = (t & mask4) + (t>>16); 477 return (int)t; 478 } 479 480 DE_INLINE int dePop64 (deUint64 a) 481 { 482 return dePop32((deUint32)(a & 0xffffffffull)) + dePop32((deUint32)(a >> 32)); 483 } 484 485 /*--------------------------------------------------------------------*//*! 486 * \brief Reverse bytes in 32-bit integer (for example MSB -> LSB). 487 * \param a Input value. 488 * \return The input with bytes reversed 489 *//*--------------------------------------------------------------------*/ 490 DE_INLINE deUint32 deReverseBytes32 (deUint32 v) 491 { 492 deUint32 b0 = v << 24; 493 deUint32 b1 = (v & 0x0000ff00) << 8; 494 deUint32 b2 = (v & 0x00ff0000) >> 8; 495 deUint32 b3 = v >> 24; 496 return b0|b1|b2|b3; 497 } 498 499 /*--------------------------------------------------------------------*//*! 500 * \brief Reverse bytes in 16-bit integer (for example MSB -> LSB). 501 * \param a Input value. 502 * \return The input with bytes reversed 503 *//*--------------------------------------------------------------------*/ 504 DE_INLINE deUint16 deReverseBytes16 (deUint16 v) 505 { 506 return (deUint16)((v << 8) | (v >> 8)); 507 } 508 509 DE_INLINE deInt32 deSafeMul32 (deInt32 a, deInt32 b) 510 { 511 deInt32 res = a * b; 512 DE_ASSERT((deInt64)res == ((deInt64)a * (deInt64)b)); 513 return res; 514 } 515 516 DE_INLINE deInt32 deSafeAdd32 (deInt32 a, deInt32 b) 517 { 518 DE_ASSERT((deInt64)a + (deInt64)b == (deInt64)(a + b)); 519 return (a + b); 520 } 521 522 DE_INLINE deInt32 deDivRoundUp32 (deInt32 a, deInt32 b) 523 { 524 return a/b + ((a%b) ? 1 : 0); 525 } 526 527 /* \todo [petri] Move to deInt64.h? */ 528 529 DE_INLINE deInt32 deMulAsr32 (deInt32 a, deInt32 b, int shift) 530 { 531 return (deInt32)(((deInt64)a * (deInt64)b) >> shift); 532 } 533 534 DE_INLINE deInt32 deSafeMulAsr32 (deInt32 a, deInt32 b, int shift) 535 { 536 deInt64 res = ((deInt64)a * (deInt64)b) >> shift; 537 DE_ASSERT(res == (deInt64)(deInt32)res); 538 return (deInt32)res; 539 } 540 541 DE_INLINE deUint32 deSafeMuluAsr32 (deUint32 a, deUint32 b, int shift) 542 { 543 deUint64 res = ((deUint64)a * (deUint64)b) >> shift; 544 DE_ASSERT(res == (deUint64)(deUint32)res); 545 return (deUint32)res; 546 } 547 548 DE_INLINE deInt64 deMul32_32_64 (deInt32 a, deInt32 b) 549 { 550 return ((deInt64)a * (deInt64)b); 551 } 552 553 DE_INLINE deInt64 deAbs64 (deInt64 a) 554 { 555 DE_ASSERT((deUint64) a != 0x8000000000000000LL); 556 return (a >= 0) ? a : -a; 557 } 558 559 DE_INLINE int deClz64 (deUint64 a) 560 { 561 if ((a >> 32) != 0) 562 return deClz32((deUint32)(a >> 32)); 563 return deClz32((deUint32)a) + 32; 564 } 565 566 /* Common hash & compare functions. */ 567 568 DE_INLINE deUint32 deInt32Hash (deInt32 a) 569 { 570 /* From: http://www.concentric.net/~Ttwang/tech/inthash.htm */ 571 deUint32 key = (deUint32)a; 572 key = (key ^ 61) ^ (key >> 16); 573 key = key + (key << 3); 574 key = key ^ (key >> 4); 575 key = key * 0x27d4eb2d; /* prime/odd constant */ 576 key = key ^ (key >> 15); 577 return key; 578 } 579 580 DE_INLINE deUint32 deInt64Hash (deInt64 a) 581 { 582 /* From: http://www.concentric.net/~Ttwang/tech/inthash.htm */ 583 deUint64 key = (deUint64)a; 584 key = (~key) + (key << 21); /* key = (key << 21) - key - 1; */ 585 key = key ^ (key >> 24); 586 key = (key + (key << 3)) + (key << 8); /* key * 265 */ 587 key = key ^ (key >> 14); 588 key = (key + (key << 2)) + (key << 4); /* key * 21 */ 589 key = key ^ (key >> 28); 590 key = key + (key << 31); 591 return (deUint32)key; 592 } 593 594 DE_INLINE deUint32 deInt16Hash (deInt16 v) { return deInt32Hash(v); } 595 DE_INLINE deUint32 deUint16Hash (deUint16 v) { return deInt32Hash((deInt32)v); } 596 DE_INLINE deUint32 deUint32Hash (deUint32 v) { return deInt32Hash((deInt32)v); } 597 DE_INLINE deUint32 deUint64Hash (deUint64 v) { return deInt64Hash((deInt64)v); } 598 599 DE_INLINE deBool deInt16Equal (deInt16 a, deInt16 b) { return (a == b); } 600 DE_INLINE deBool deUint16Equal (deUint16 a, deUint16 b) { return (a == b); } 601 DE_INLINE deBool deInt32Equal (deInt32 a, deInt32 b) { return (a == b); } 602 DE_INLINE deBool deUint32Equal (deUint32 a, deUint32 b) { return (a == b); } 603 DE_INLINE deBool deInt64Equal (deInt64 a, deInt64 b) { return (a == b); } 604 DE_INLINE deBool deUint64Equal (deUint64 a, deUint64 b) { return (a == b); } 605 606 DE_INLINE deUint32 dePointerHash (const void* ptr) 607 { 608 deUintptr val = (deUintptr)ptr; 609 #if (DE_PTR_SIZE == 4) 610 return deInt32Hash((int)val); 611 #elif (DE_PTR_SIZE == 8) 612 return deInt64Hash((deInt64)val); 613 #else 614 # error Unsupported pointer size. 615 #endif 616 } 617 618 DE_INLINE deBool dePointerEqual (const void* a, const void* b) 619 { 620 return (a == b); 621 } 622 623 /** 624 * \brief Modulo that generates the same sign as divisor and rounds toward 625 * negative infinity -- assuming c99 %-operator. 626 */ 627 DE_INLINE deInt32 deInt32ModF (deInt32 n, deInt32 d) 628 { 629 deInt32 r = n%d; 630 if ((r > 0 && d < 0) || (r < 0 && d > 0)) r = r+d; 631 return r; 632 } 633 634 DE_INLINE deBool deInt64InInt32Range (deInt64 x) 635 { 636 return ((x >= (((deInt64)((deInt32)(-0x7FFFFFFF - 1))))) && (x <= ((1ll<<31)-1))); 637 } 638 639 640 DE_INLINE deUint32 deBitMask32 (int leastSignificantBitNdx, int numBits) 641 { 642 DE_ASSERT(deInRange32(leastSignificantBitNdx, 0, 32)); 643 DE_ASSERT(deInRange32(numBits, 0, 32)); 644 DE_ASSERT(deInRange32(leastSignificantBitNdx+numBits, 0, 32)); 645 646 if (numBits < 32 && leastSignificantBitNdx < 32) 647 return ((1u<<numBits)-1u) << (deUint32)leastSignificantBitNdx; 648 else if (numBits == 0 && leastSignificantBitNdx == 32) 649 return 0u; 650 else 651 { 652 DE_ASSERT(numBits == 32 && leastSignificantBitNdx == 0); 653 return 0xFFFFFFFFu; 654 } 655 } 656 657 DE_INLINE deUint32 deUintMaxValue32 (int numBits) 658 { 659 DE_ASSERT(deInRange32(numBits, 1, 32)); 660 if (numBits < 32) 661 return ((1u<<numBits)-1u); 662 else 663 return 0xFFFFFFFFu; 664 } 665 666 DE_INLINE deInt32 deIntMaxValue32 (int numBits) 667 { 668 DE_ASSERT(deInRange32(numBits, 1, 32)); 669 if (numBits < 32) 670 return ((deInt32)1 << (numBits - 1)) - 1; 671 else 672 { 673 /* avoid undefined behavior of int overflow when shifting */ 674 return 0x7FFFFFFF; 675 } 676 } 677 678 DE_INLINE deInt32 deIntMinValue32 (int numBits) 679 { 680 DE_ASSERT(deInRange32(numBits, 1, 32)); 681 if (numBits < 32) 682 return -((deInt32)1 << (numBits - 1)); 683 else 684 { 685 /* avoid undefined behavior of int overflow when shifting */ 686 return (deInt32)(-0x7FFFFFFF - 1); 687 } 688 } 689 690 DE_INLINE deInt32 deSignExtendTo32 (deInt32 value, int numBits) 691 { 692 DE_ASSERT(deInRange32(numBits, 1, 32)); 693 694 if (numBits < 32) 695 { 696 deBool signSet = ((deUint32)value & (1u<<(numBits-1))) != 0; 697 deUint32 signMask = deBitMask32(numBits, 32-numBits); 698 699 DE_ASSERT(((deUint32)value & signMask) == 0u); 700 701 return (deInt32)((deUint32)value | (signSet ? signMask : 0u)); 702 } 703 else 704 return value; 705 } 706 707 DE_END_EXTERN_C 708 709 #endif /* _DEINT32_H */ 710