byte_safe_strings.php 5.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181
  1. <?php
  2. /**
  3. * Random_* Compatibility Library
  4. * for using the new PHP 7 random_* API in PHP 5 projects
  5. *
  6. * The MIT License (MIT)
  7. *
  8. * Copyright (c) 2015 - 2017 Paragon Initiative Enterprises
  9. *
  10. * Permission is hereby granted, free of charge, to any person obtaining a copy
  11. * of this software and associated documentation files (the "Software"), to deal
  12. * in the Software without restriction, including without limitation the rights
  13. * to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
  14. * copies of the Software, and to permit persons to whom the Software is
  15. * furnished to do so, subject to the following conditions:
  16. *
  17. * The above copyright notice and this permission notice shall be included in
  18. * all copies or substantial portions of the Software.
  19. *
  20. * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
  21. * IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
  22. * FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
  23. * AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
  24. * LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
  25. * OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
  26. * SOFTWARE.
  27. */
  28. if (!is_callable('RandomCompat_strlen')) {
  29. if (
  30. defined('MB_OVERLOAD_STRING') &&
  31. ini_get('mbstring.func_overload') & MB_OVERLOAD_STRING
  32. ) {
  33. /**
  34. * strlen() implementation that isn't brittle to mbstring.func_overload
  35. *
  36. * This version uses mb_strlen() in '8bit' mode to treat strings as raw
  37. * binary rather than UTF-8, ISO-8859-1, etc
  38. *
  39. * @param string $binary_string
  40. *
  41. * @throws TypeError
  42. *
  43. * @return int
  44. */
  45. function RandomCompat_strlen($binary_string)
  46. {
  47. if (!is_string($binary_string)) {
  48. throw new TypeError(
  49. 'RandomCompat_strlen() expects a string'
  50. );
  51. }
  52. return (int) mb_strlen($binary_string, '8bit');
  53. }
  54. } else {
  55. /**
  56. * strlen() implementation that isn't brittle to mbstring.func_overload
  57. *
  58. * This version just used the default strlen()
  59. *
  60. * @param string $binary_string
  61. *
  62. * @throws TypeError
  63. *
  64. * @return int
  65. */
  66. function RandomCompat_strlen($binary_string)
  67. {
  68. if (!is_string($binary_string)) {
  69. throw new TypeError(
  70. 'RandomCompat_strlen() expects a string'
  71. );
  72. }
  73. return (int) strlen($binary_string);
  74. }
  75. }
  76. }
  77. if (!is_callable('RandomCompat_substr')) {
  78. if (
  79. defined('MB_OVERLOAD_STRING')
  80. &&
  81. ini_get('mbstring.func_overload') & MB_OVERLOAD_STRING
  82. ) {
  83. /**
  84. * substr() implementation that isn't brittle to mbstring.func_overload
  85. *
  86. * This version uses mb_substr() in '8bit' mode to treat strings as raw
  87. * binary rather than UTF-8, ISO-8859-1, etc
  88. *
  89. * @param string $binary_string
  90. * @param int $start
  91. * @param int $length (optional)
  92. *
  93. * @throws TypeError
  94. *
  95. * @return string
  96. */
  97. function RandomCompat_substr($binary_string, $start, $length = null)
  98. {
  99. if (!is_string($binary_string)) {
  100. throw new TypeError(
  101. 'RandomCompat_substr(): First argument should be a string'
  102. );
  103. }
  104. if (!is_int($start)) {
  105. throw new TypeError(
  106. 'RandomCompat_substr(): Second argument should be an integer'
  107. );
  108. }
  109. if ($length === null) {
  110. /**
  111. * mb_substr($str, 0, NULL, '8bit') returns an empty string on
  112. * PHP 5.3, so we have to find the length ourselves.
  113. */
  114. $length = RandomCompat_strlen($binary_string) - $start;
  115. } elseif (!is_int($length)) {
  116. throw new TypeError(
  117. 'RandomCompat_substr(): Third argument should be an integer, or omitted'
  118. );
  119. }
  120. // Consistency with PHP's behavior
  121. if ($start === RandomCompat_strlen($binary_string) && $length === 0) {
  122. return '';
  123. }
  124. if ($start > RandomCompat_strlen($binary_string)) {
  125. return '';
  126. }
  127. return (string) mb_substr($binary_string, $start, $length, '8bit');
  128. }
  129. } else {
  130. /**
  131. * substr() implementation that isn't brittle to mbstring.func_overload
  132. *
  133. * This version just uses the default substr()
  134. *
  135. * @param string $binary_string
  136. * @param int $start
  137. * @param int $length (optional)
  138. *
  139. * @throws TypeError
  140. *
  141. * @return string
  142. */
  143. function RandomCompat_substr($binary_string, $start, $length = null)
  144. {
  145. if (!is_string($binary_string)) {
  146. throw new TypeError(
  147. 'RandomCompat_substr(): First argument should be a string'
  148. );
  149. }
  150. if (!is_int($start)) {
  151. throw new TypeError(
  152. 'RandomCompat_substr(): Second argument should be an integer'
  153. );
  154. }
  155. if ($length !== null) {
  156. if (!is_int($length)) {
  157. throw new TypeError(
  158. 'RandomCompat_substr(): Third argument should be an integer, or omitted'
  159. );
  160. }
  161. return (string) substr($binary_string, $start, $length);
  162. }
  163. return (string) substr($binary_string, $start);
  164. }
  165. }
  166. }