From 6405e2ea6e0d374e490dae3fb43eefcb2d00cd25 Mon Sep 17 00:00:00 2001 From: Jonas 'Sortie' Termansen Date: Sun, 10 May 2015 22:24:45 +0200 Subject: [PATCH] Add arc4random support to the kernel. --- kernel/include/sortix/kernel/random.h | 39 +++++++++++++++++++++++++++ kernel/random.cpp | 29 +++++++++++++++++--- libc/Makefile | 6 ++--- libc/stdlib/arc4random_buf.cpp | 27 ++++++++++++++++++- 4 files changed, 94 insertions(+), 7 deletions(-) create mode 100644 kernel/include/sortix/kernel/random.h diff --git a/kernel/include/sortix/kernel/random.h b/kernel/include/sortix/kernel/random.h new file mode 100644 index 00000000..630807f7 --- /dev/null +++ b/kernel/include/sortix/kernel/random.h @@ -0,0 +1,39 @@ +/******************************************************************************* + + Copyright(C) Jonas 'Sortie' Termansen 2015. + + This file is part of Sortix. + + Sortix is free software: you can redistribute it and/or modify it under the + terms of the GNU General Public License as published by the Free Software + Foundation, either version 3 of the License, or (at your option) any later + version. + + Sortix is distributed in the hope that it will be useful, but WITHOUT ANY + WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS + FOR A PARTICULAR PURPOSE. See the GNU General Public License for more + details. + + You should have received a copy of the GNU General Public License along with + Sortix. If not, see . + + sortix/kernel/random.h + Kernel entropy gathering. + +*******************************************************************************/ + +#ifndef INCLUDE_SORTIX_KERNEL_RANDOM_H +#define INCLUDE_SORTIX_KERNEL_RANDOM_H + +#include + +namespace Sortix { +namespace Random { + +bool HasEntropy(); +void GetEntropy(void* buffer, size_t size); + +} // namespace Random +} // namespace Sortix + +#endif diff --git a/kernel/random.cpp b/kernel/random.cpp index 85a1d84d..7aaf51ee 100644 --- a/kernel/random.cpp +++ b/kernel/random.cpp @@ -1,6 +1,6 @@ /******************************************************************************* - Copyright(C) Jonas 'Sortie' Termansen 2014. + Copyright(C) Jonas 'Sortie' Termansen 2014, 2015. This file is part of Sortix. @@ -23,6 +23,8 @@ *******************************************************************************/ #include +#include +#include #include @@ -32,10 +34,17 @@ #include namespace Sortix { +namespace Random { static unsigned long sequence = 0; -int sys_getentropy(void* user_buffer, size_t size) +bool HasEntropy() +{ + // We only have new entropy once and that's at boot. + return sequence == 0; +} + +void GetEntropy(void* result, size_t size) { union { @@ -48,7 +57,7 @@ int sys_getentropy(void* user_buffer, size_t size) } seed; }; if ( sizeof(buffer) < size ) - return errno = EIO, -1; + size = sizeof(buffer); // TODO: SECURITY: We need to actually gather entropy and deliver it. for ( size_t i = 0; i < size; i++ ) buffer[i] = i; @@ -60,6 +69,20 @@ int sys_getentropy(void* user_buffer, size_t size) seed.realtime = Time::Get(CLOCK_REALTIME); seed.monotonic = Time::Get(CLOCK_MONOTONIC); seed.sequence = InterlockedIncrement(&sequence).o; + memcpy(result, buffer, size); +} + +} // namespace Random +} // namespace Sortix + +namespace Sortix { + +int sys_getentropy(void* user_buffer, size_t size) +{ + unsigned char buffer[256]; + if ( sizeof(buffer) < size ) + return errno = EIO, -1; + arc4random_buf(buffer, sizeof(buffer)); if ( !CopyToUser(user_buffer, buffer, size) ) return -1; return 0; diff --git a/libc/Makefile b/libc/Makefile index d4d1708b..3bdd12d7 100644 --- a/libc/Makefile +++ b/libc/Makefile @@ -153,6 +153,9 @@ stdio/vsprintf.o \ stdio/vsscanf.o \ stdlib/abort.o \ stdlib/abs.o \ +stdlib/arc4random_buf.o \ +stdlib/arc4random.o \ +stdlib/arc4random_uniform.o \ stdlib/atof.o \ stdlib/atoi.o \ stdlib/atoll.o \ @@ -432,9 +435,6 @@ stdio/tmpfile.o \ stdio/vfprintf.o \ stdio/vprintf.o \ stdio/vscanf.o \ -stdlib/arc4random_buf.o \ -stdlib/arc4random.o \ -stdlib/arc4random_uniform.o \ stdlib/atexit.o \ stdlib/canonicalize_file_name_at.o \ stdlib/canonicalize_file_name.o \ diff --git a/libc/stdlib/arc4random_buf.cpp b/libc/stdlib/arc4random_buf.cpp index 143a4837..3b9c463e 100644 --- a/libc/stdlib/arc4random_buf.cpp +++ b/libc/stdlib/arc4random_buf.cpp @@ -26,16 +26,32 @@ * Public domain. */ -/* Adapted for Sortix libc by Jonas 'Sortie' Termansen in 2014. */ +/* Adapted for Sortix libc by Jonas 'Sortie' Termansen in 2014, 2015. */ #include #include #include #include #include +#if !defined(__is_sortix_kernel) #include +#endif #include +#if defined(__is_sortix_kernel) +#include +#include +#endif + +#if defined(__is_sortix_kernel) +#define PTHREAD_MUTEX_INITIALIZER Sortix::KTHREAD_MUTEX_INITIALIZER +#define pthread_mutex_t Sortix::kthread_mutex_t +#define pthread_mutex_lock Sortix::kthread_mutex_lock +#define pthread_mutex_unlock Sortix::kthread_mutex_unlock +#define getpid() 0 +#define getentropy Sortix::Random::GetEntropy +#endif + struct chacha { uint32_t input[16]; @@ -163,6 +179,15 @@ extern "C" void arc4random_buf(void* buffer_ptr, size_t size) pthread_mutex_lock(&arc4random_mutex); +#if defined(__is_sortix_kernel) + if ( Sortix::Random::HasEntropy() ) + { + rs_count = 0; + rs_have = 0; + memset(rs_buf, 0, sizeof(rs_buf)); + } +#endif + /* TODO: Employ zero-memory-on-fork semantics instead. */ /* pid_t are never reused on Sortix at the moment. */ if ( getpid() != rs_pid )