zephyr/drivers/entropy/fake_entropy_native_posix.c
Alberto Escolar Piedras e58a491900 entropy: native_posix: Add kconfig to not seed by default
Provide a new kconfig option which can be used to disable
the default seeding of the host standard library random
generator by this driver.
This allows some other component to do so without this component
default initialization interfering.

Signed-off-by: Alberto Escolar Piedras <alberto.escolar.piedras@nordicsemi.no>
2024-09-05 16:56:33 -04:00

127 lines
3.1 KiB
C

/*
* Copyright (c) 2018 Oticon A/S
*
* SPDX-License-Identifier: Apache-2.0
*
* Pseudo-random entropy generator for the ARCH_POSIX architecture:
* Following the principle of reproducibility of the native_posix board
* this entropy device will always generate the same random sequence when
* initialized with the same seed
*
* This entropy source should only be used for testing.
*/
#define DT_DRV_COMPAT zephyr_native_posix_rng
#include <zephyr/device.h>
#include <zephyr/drivers/entropy.h>
#include <zephyr/init.h>
#include <zephyr/sys/util.h>
#include <stdlib.h>
#include <string.h>
#include <zephyr/arch/posix/posix_trace.h>
#include "soc.h"
#include "cmdline.h" /* native_posix command line options header */
#include "nsi_host_trampolines.h"
#include "fake_entropy_native_bottom.h"
static unsigned int seed = 0x5678;
static bool seed_random;
static bool seed_set;
static int entropy_native_posix_get_entropy(const struct device *dev,
uint8_t *buffer,
uint16_t length)
{
ARG_UNUSED(dev);
while (length) {
/*
* Note that only 1 thread (Zephyr thread or HW models), runs at
* a time, therefore there is no need to use random_r()
*/
long value = nsi_host_random();
size_t to_copy = MIN(length, sizeof(long int));
memcpy(buffer, &value, to_copy);
buffer += to_copy;
length -= to_copy;
}
return 0;
}
static int entropy_native_posix_get_entropy_isr(const struct device *dev,
uint8_t *buf,
uint16_t len, uint32_t flags)
{
ARG_UNUSED(flags);
/*
* entropy_native_posix_get_entropy() is also safe for ISRs
* and always produces data.
*/
entropy_native_posix_get_entropy(dev, buf, len);
return len;
}
static int entropy_native_posix_init(const struct device *dev)
{
ARG_UNUSED(dev);
if (seed_set || seed_random ||
IS_ENABLED(CONFIG_FAKE_ENTROPY_NATIVE_POSIX_SEED_BY_DEFAULT)) {
entropy_native_seed(seed, seed_random);
}
posix_print_warning("WARNING: "
"Using a test - not safe - entropy source\n");
return 0;
}
static const struct entropy_driver_api entropy_native_posix_api_funcs = {
.get_entropy = entropy_native_posix_get_entropy,
.get_entropy_isr = entropy_native_posix_get_entropy_isr
};
DEVICE_DT_INST_DEFINE(0,
entropy_native_posix_init, NULL,
NULL, NULL,
PRE_KERNEL_1, CONFIG_ENTROPY_INIT_PRIORITY,
&entropy_native_posix_api_funcs);
static void seed_was_set(char *argv, int offset)
{
ARG_UNUSED(argv);
ARG_UNUSED(offset);
seed_set = true;
}
static void add_fake_entropy_option(void)
{
static struct args_struct_t entropy_options[] = {
{
.option = "seed",
.name = "r_seed",
.type = 'u',
.dest = (void *)&seed,
.call_when_found = seed_was_set,
.descript = "A 32-bit integer seed value for the entropy device, such as "
"97229 (decimal), 0x17BCD (hex), or 0275715 (octal)"
},
{
.is_switch = true,
.option = "seed-random",
.type = 'b',
.dest = (void *)&seed_random,
.descript = "Seed the random generator from /dev/urandom. "
"Note your test may not be reproducible if you set this option"
},
ARG_TABLE_ENDMARKER
};
native_add_command_line_opts(entropy_options);
}
NATIVE_TASK(add_fake_entropy_option, PRE_BOOT_1, 10);