Path: blob/main/crypto/libecc/src/external_deps/rand.c
34878 views
/*1* Copyright (C) 2017 - This file is part of libecc project2*3* Authors:4* Ryad BENADJILA <[email protected]>5* Arnaud EBALARD <[email protected]>6* Jean-Pierre FLORI <[email protected]>7*8* Contributors:9* Nicolas VIVET <[email protected]>10* Karim KHALFALLAH <[email protected]>11*12* This software is licensed under a dual BSD and GPL v2 license.13* See LICENSE file at the root folder of the project.14*/15#include <libecc/external_deps/rand.h>1617/* Unix and compatible case (including macOS) */18#if defined(WITH_STDLIB) && (defined(__unix__) || defined(__APPLE__))19#include <stdio.h>20#include <stdlib.h>21#include <string.h>22#include <limits.h>2324#include <sys/types.h>25#include <sys/stat.h>26#include <fcntl.h>27#include <unistd.h>28#include <libecc/words/words.h>2930/*31* Copy file content to buffer. Return 0 on success, i.e. if the request32* size has been read and copied to buffer and -1 otherwise.33*/34ATTRIBUTE_WARN_UNUSED_RET static int fimport(unsigned char *buf, u16 buflen,35const char *path)36{37u16 rem = buflen, copied = 0;38ssize_t ret;39int fd;4041if ((buf == NULL) || (path == NULL)) {42ret = -1;43goto err;44}4546fd = open(path, O_RDONLY);47if (fd == -1) {48printf("Unable to open input file %s\n", path);49ret = -1;50goto err;51}5253while (rem) {54ret = (int)read(fd, buf + copied, rem);55if (ret <= 0) {56break;57} else {58rem = (u16)(rem - ret);59copied = (u16)(copied + ret);60}61}6263if (close(fd)) {64printf("Unable to close input file %s\n", path);65ret = -1;66goto err;67}6869ret = (copied == buflen) ? 0 : -1;7071err:72return (int)ret;73}7475int get_random(unsigned char *buf, u16 len)76{77return fimport(buf, len, "/dev/urandom");78}7980/* Windows case */81#elif defined(WITH_STDLIB) && defined(__WIN32__)82#include <windows.h>83#include <wincrypt.h>8485int get_random(unsigned char *buf, u16 len)86{87int ret;88HCRYPTPROV hCryptProv = 0;8990if (CryptAcquireContext(&hCryptProv, NULL, NULL,91PROV_RSA_FULL, CRYPT_VERIFYCONTEXT) == FALSE) {92ret = -1;93goto err;94}9596if (CryptGenRandom(hCryptProv, len, buf) == FALSE) {97CryptReleaseContext(hCryptProv, 0);98ret = -1;99goto err;100}101CryptReleaseContext(hCryptProv, 0);102ret = 0;103104err:105return ret;106}107108/* No platform detected, the user must provide an implementation! */109#else110/* WARNING: when providing/implementing the get_random function, one must:111* - Use a proper entropy source with a TRNG (True Random Number Generator)112* basis and clean PRNG (Pseudo-Random Number Generator) post-processing113* when needed.114* - Use a non-leaking generator in contexts where attackers that have access115* to side channels are a plausible threat (a process in an OS sharing memory116* and caches with other possibly malicious processes, a microcontroller117* that can be observed using EM probes or power consumtion, ...).118*/119#error "rand.c: you have to implement get_random with a proper entropy source!"120#endif121122123