Skip to content

Commit b610c0f

Browse files
authored
[k2] implement random_bytes function (#1491)
1 parent 1a61c6a commit b610c0f

File tree

3 files changed

+34
-3
lines changed

3 files changed

+34
-3
lines changed

builtin-functions/kphp-light/stdlib/math-functions.txt

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -164,6 +164,8 @@ function levenshtein ($str1 ::: string, $str2 ::: string) ::: int;
164164

165165
function lcg_value() ::: float;
166166

167+
function random_bytes($length ::: int) ::: string | false;
168+
167169
/** @kphp-extern-func-info interruptible */
168170
function uniqid ($prefix ::: string = '', $more_entropy ::: bool = false) ::: string;
169171

@@ -185,5 +187,3 @@ define('PHP_ROUND_HALF_ODD', 123423146);
185187

186188
/** @kphp-extern-func-info stub generation-required */
187189
function random_int($l ::: int, $r ::: int) ::: int | false;
188-
/** @kphp-extern-func-info stub generation-required */
189-
function random_bytes($length ::: int) ::: string | false;

runtime-light/stdlib/math/random-functions.h

Lines changed: 31 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -15,6 +15,12 @@
1515
#include <random>
1616
#include <utility>
1717

18+
#if defined(__APPLE__)
19+
#include <stdlib.h>
20+
#else
21+
#include <sys/random.h>
22+
#endif
23+
1824
#include "runtime-common/core/runtime-core.h"
1925
#include "runtime-common/stdlib/math/random-functions.h"
2026
#include "runtime-light/coroutine/task.h"
@@ -83,6 +89,15 @@ inline int64_t lcg_modmult(int64_t a, int64_t b, int64_t c, int64_t m, int64_t s
8389
return res;
8490
}
8591

92+
inline int64_t secure_rand_buf(void* const buf, size_t length) noexcept {
93+
#if defined(__APPLE__)
94+
arc4random_buf(buf, length);
95+
return 0;
96+
#else
97+
return getrandom(buf, length, GRND_NONBLOCK);
98+
#endif
99+
}
100+
86101
// Analogue of unix's `gettimeofday`
87102
// Returns seconds elapsed since Epoch, and milliseconds elapsed from the last second.
88103
inline std::pair<std::chrono::seconds, std::chrono::microseconds> system_seconds_and_micros() noexcept {
@@ -126,6 +141,22 @@ inline double f$lcg_value() noexcept {
126141
return static_cast<double>(z) * random_impl_::lcg_value_coef;
127142
}
128143

144+
inline Optional<string> f$random_bytes(int64_t length) noexcept {
145+
if (length < 1) [[unlikely]] {
146+
kphp::log::warning("argument #1 ($length) must be greater than 0");
147+
return false;
148+
}
149+
150+
string str{static_cast<string::size_type>(length), false};
151+
152+
if (random_impl_::secure_rand_buf(static_cast<void*>(str.buffer()), static_cast<size_t>(length)) == -1) {
153+
kphp::log::warning("source of randomness cannot be found");
154+
return false;
155+
}
156+
157+
return str;
158+
}
159+
129160
inline kphp::coro::task<string> f$uniqid(string prefix = string{}, bool more_entropy = false) noexcept {
130161
if (!more_entropy) {
131162
co_await f$usleep(1);

tests/phpt/dl/385_random_bytes.php

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,4 @@
1-
@ok php8 k2_skip
1+
@ok php8
22
<?php
33

44
function test_random_bytes() {

0 commit comments

Comments
 (0)