diff options
author | Sergey Bugaev <bugaevc@gmail.com> | 2022-12-02 16:55:58 +0300 |
---|---|---|
committer | Samuel Thibault <samuel.thibault@ens-lyon.org> | 2022-12-02 22:33:49 +0100 |
commit | 8fb923ddc38dd5f4bfac4869d70fd80483fdb87a (patch) | |
tree | 59ddca4a285e060ff066d57d2c88b84391599c81 /sysdeps/powerpc | |
parent | 2f47198b04a02097f438ecb765306fa39568a006 (diff) | |
download | glibc-8fb923ddc38dd5f4bfac4869d70fd80483fdb87a.tar.gz glibc-8fb923ddc38dd5f4bfac4869d70fd80483fdb87a.tar.xz glibc-8fb923ddc38dd5f4bfac4869d70fd80483fdb87a.zip |
hurd: Make getrandom cache the server port
Previously, getrandom would, each time it's called, traverse the file system to find /dev/urandom, fetch some random data from it, then throw away that port. This is quite slow, while calls to getrandom are genrally expected to be fast. Additionally, this means that getrandom can not work when /dev/urandom is unavailable, such as inside a chroot that lacks one. User programs expect calls to getrandom to work inside a chroot if they first call getrandom outside of the chroot. In particular, this is known to break the OpenSSH server, and in that case the issue is exacerbated by the API of arc4random, which prevents it from properly reporting errors, forcing glibc to abort on failure. This causes sshd to just die once it tries to generate a random number. Caching the random server port, in a manner similar to how socket server ports are cached, both improves the performance and works around the chroot issue. Tested on i686-gnu with the following program: pthread_barrier_t barrier; void *worker(void*) { pthread_barrier_wait(&barrier); uint32_t sum = 0; for (int i = 0; i < 10000; i++) { sum += arc4random(); } return (void *)(uintptr_t) sum; } int main() { pthread_t threads[THREAD_COUNT]; pthread_barrier_init(&barrier, NULL, THREAD_COUNT); for (int i = 0; i < THREAD_COUNT; i++) { pthread_create(&threads[i], NULL, worker, NULL); } for (int i = 0; i < THREAD_COUNT; i++) { void *retval; pthread_join(threads[i], &retval); printf("Thread %i: %lu\n", i, (unsigned long)(uintptr_t) retval); } In my totally unscientific benchmark, with this patch, this completes in about 7 seconds, whereas previously it took about 50 seconds. This program was also used to test that getrandom () doesn't explode if the random server dies, but instead reopens the /dev/urandom anew. I have also verified that with this patch, OpenSSH can once again accept connections properly. Signed-off-by: Sergey Bugaev <bugaevc@gmail.com> Message-Id: <20221202135558.23781-1-bugaevc@gmail.com>
Diffstat (limited to 'sysdeps/powerpc')
0 files changed, 0 insertions, 0 deletions