bitrotate.h 4.5 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138
  1. /* bitrotate.h - Rotate bits in integers
  2. Copyright (C) 2008-2020 Free Software Foundation, Inc.
  3. This program is free software: you can redistribute it and/or modify
  4. it under the terms of the GNU General Public License as published by
  5. the Free Software Foundation; either version 3 of the License, or
  6. (at your option) any later version.
  7. This program is distributed in the hope that it will be useful,
  8. but WITHOUT ANY WARRANTY; without even the implied warranty of
  9. MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
  10. GNU General Public License for more details.
  11. You should have received a copy of the GNU General Public License
  12. along with this program. If not, see <https://www.gnu.org/licenses/>. */
  13. /* Written by Simon Josefsson <simon@josefsson.org>, 2008. */
  14. #ifndef _GL_BITROTATE_H
  15. #define _GL_BITROTATE_H
  16. #include <limits.h>
  17. #include <stdint.h>
  18. #include <sys/types.h>
  19. #ifndef _GL_INLINE_HEADER_BEGIN
  20. #error "Please include config.h first."
  21. #endif
  22. _GL_INLINE_HEADER_BEGIN
  23. #ifndef BITROTATE_INLINE
  24. # define BITROTATE_INLINE _GL_INLINE
  25. #endif
  26. #ifdef UINT64_MAX
  27. /* Given an unsigned 64-bit argument X, return the value corresponding
  28. to rotating the bits N steps to the left. N must be between 1 and
  29. 63 inclusive. */
  30. BITROTATE_INLINE uint64_t
  31. rotl64 (uint64_t x, int n)
  32. {
  33. return ((x << n) | (x >> (64 - n))) & UINT64_MAX;
  34. }
  35. /* Given an unsigned 64-bit argument X, return the value corresponding
  36. to rotating the bits N steps to the right. N must be between 1 to
  37. 63 inclusive.*/
  38. BITROTATE_INLINE uint64_t
  39. rotr64 (uint64_t x, int n)
  40. {
  41. return ((x >> n) | (x << (64 - n))) & UINT64_MAX;
  42. }
  43. #endif
  44. /* Given an unsigned 32-bit argument X, return the value corresponding
  45. to rotating the bits N steps to the left. N must be between 1 and
  46. 31 inclusive. */
  47. BITROTATE_INLINE uint32_t
  48. rotl32 (uint32_t x, int n)
  49. {
  50. return ((x << n) | (x >> (32 - n))) & UINT32_MAX;
  51. }
  52. /* Given an unsigned 32-bit argument X, return the value corresponding
  53. to rotating the bits N steps to the right. N must be between 1 to
  54. 31 inclusive.*/
  55. BITROTATE_INLINE uint32_t
  56. rotr32 (uint32_t x, int n)
  57. {
  58. return ((x >> n) | (x << (32 - n))) & UINT32_MAX;
  59. }
  60. /* Given a size_t argument X, return the value corresponding
  61. to rotating the bits N steps to the left. N must be between 1 and
  62. (CHAR_BIT * sizeof (size_t) - 1) inclusive. */
  63. BITROTATE_INLINE size_t
  64. rotl_sz (size_t x, int n)
  65. {
  66. return ((x << n) | (x >> ((CHAR_BIT * sizeof x) - n))) & SIZE_MAX;
  67. }
  68. /* Given a size_t argument X, return the value corresponding
  69. to rotating the bits N steps to the right. N must be between 1 to
  70. (CHAR_BIT * sizeof (size_t) - 1) inclusive. */
  71. BITROTATE_INLINE size_t
  72. rotr_sz (size_t x, int n)
  73. {
  74. return ((x >> n) | (x << ((CHAR_BIT * sizeof x) - n))) & SIZE_MAX;
  75. }
  76. /* Given an unsigned 16-bit argument X, return the value corresponding
  77. to rotating the bits N steps to the left. N must be between 1 to
  78. 15 inclusive, but on most relevant targets N can also be 0 and 16
  79. because 'int' is at least 32 bits and the arguments must widen
  80. before shifting. */
  81. BITROTATE_INLINE uint16_t
  82. rotl16 (uint16_t x, int n)
  83. {
  84. return (((unsigned int) x << n) | ((unsigned int) x >> (16 - n)))
  85. & UINT16_MAX;
  86. }
  87. /* Given an unsigned 16-bit argument X, return the value corresponding
  88. to rotating the bits N steps to the right. N must be in 1 to 15
  89. inclusive, but on most relevant targets N can also be 0 and 16
  90. because 'int' is at least 32 bits and the arguments must widen
  91. before shifting. */
  92. BITROTATE_INLINE uint16_t
  93. rotr16 (uint16_t x, int n)
  94. {
  95. return (((unsigned int) x >> n) | ((unsigned int) x << (16 - n)))
  96. & UINT16_MAX;
  97. }
  98. /* Given an unsigned 8-bit argument X, return the value corresponding
  99. to rotating the bits N steps to the left. N must be between 1 to 7
  100. inclusive, but on most relevant targets N can also be 0 and 8
  101. because 'int' is at least 32 bits and the arguments must widen
  102. before shifting. */
  103. BITROTATE_INLINE uint8_t
  104. rotl8 (uint8_t x, int n)
  105. {
  106. return (((unsigned int) x << n) | ((unsigned int) x >> (8 - n))) & UINT8_MAX;
  107. }
  108. /* Given an unsigned 8-bit argument X, return the value corresponding
  109. to rotating the bits N steps to the right. N must be in 1 to 7
  110. inclusive, but on most relevant targets N can also be 0 and 8
  111. because 'int' is at least 32 bits and the arguments must widen
  112. before shifting. */
  113. BITROTATE_INLINE uint8_t
  114. rotr8 (uint8_t x, int n)
  115. {
  116. return (((unsigned int) x >> n) | ((unsigned int) x << (8 - n))) & UINT8_MAX;
  117. }
  118. _GL_INLINE_HEADER_END
  119. #endif /* _GL_BITROTATE_H */