blob: 28d62c904fa89ec47232d531a7b255de26b156b2 [file] [log] [blame]
/*
* Copyright (c) 2025 Henrik Brix Andersen <henrik@brixandersen.dk>
* SPDX-License-Identifier: Apache-2.0
*/
#include <cmdline.h>
#include <nsi_host_trampolines.h>
#include <posix_native_task.h>
#include <string.h>
#include <zephyr/drivers/hwinfo.h>
#include <zephyr/sys/byteorder.h>
#include "hwinfo_native_bottom.h"
static uint32_t native_hwinfo_device_id;
static bool native_hwinfo_device_id_set;
static uint32_t native_hwinfo_reset_cause;
ssize_t z_impl_hwinfo_get_device_id(uint8_t *buffer, size_t length)
{
if (length > sizeof(native_hwinfo_device_id)) {
length = sizeof(native_hwinfo_device_id);
}
sys_put_be(buffer, &native_hwinfo_device_id, length);
return length;
}
int z_impl_hwinfo_get_reset_cause(uint32_t *cause)
{
*cause = native_hwinfo_reset_cause;
return 0;
}
int z_impl_hwinfo_clear_reset_cause(void)
{
native_hwinfo_reset_cause = 0;
return 0;
}
int z_impl_hwinfo_get_supported_reset_cause(uint32_t *supported)
{
*supported = RESET_POR | RESET_SOFTWARE;
return 0;
}
static void native_hwinfo_gethostid(void)
{
if (!native_hwinfo_device_id_set) {
native_hwinfo_device_id = native_hwinfo_gethostid_bottom();
}
}
static void native_hwinfo_device_id_was_set(char *argv, int offset)
{
ARG_UNUSED(argv);
ARG_UNUSED(offset);
native_hwinfo_device_id_set = true;
}
static void native_hwinfo_add_options(void)
{
static struct args_struct_t native_hwinfo_options[] = {
{
.option = "device_id",
.name = "id",
.type = 'u',
.dest = (void *)&native_hwinfo_device_id,
.call_when_found = native_hwinfo_device_id_was_set,
.descript = "A 32-bit integer value to use as HWINFO device ID. "
"If not set, the host gethostid() output will be used.",
},
ARG_TABLE_ENDMARKER,
};
native_add_command_line_opts(native_hwinfo_options);
}
static void native_hwinfo_get_reset_cause(void)
{
/* If CONFIG_NATIVE_SIM_REBOOT was set, and a reboot was triggered, this
* environment variable would be set. Otherwise it is not expected to
* exist. Note this environment variable is not an stable API of any kind
*/
const char *cause = nsi_host_getenv("NATIVE_SIM_RESET_CAUSE");
if (!cause) {
/* Default to POR if not set */
native_hwinfo_reset_cause = RESET_POR;
return;
}
if (strcmp(cause, "SOFTWARE") == 0) {
native_hwinfo_reset_cause = RESET_SOFTWARE;
} else {
posix_print_warning("NATIVE_SIM_RESET_CAUSE (%s) set to an unknown reset cause, "
"defaulting to POR\n",
cause);
native_hwinfo_reset_cause = RESET_POR;
}
}
NATIVE_TASK(native_hwinfo_add_options, PRE_BOOT_1, 10);
NATIVE_TASK(native_hwinfo_gethostid, PRE_BOOT_2, 10);
NATIVE_TASK(native_hwinfo_get_reset_cause, PRE_BOOT_2, 10);