blob: 707ce8dd1c5780b07e1b03eab3e037c1444735f6 [file] [log] [blame]
// SPDX-License-Identifier: GPL-2.0-only
/*
* SBI verification
*
* Copyright (C) 2023, Ventana Micro Systems Inc., Andrew Jones <ajones@ventanamicro.com>
*/
#include <libcflat.h>
#include <stdlib.h>
#include <asm/sbi.h>
static void help(void)
{
puts("Test SBI\n");
puts("An environ must be provided where expected values are given.\n");
}
static struct sbiret __base_sbi_ecall(int fid, unsigned long arg0)
{
return sbi_ecall(SBI_EXT_BASE, fid, arg0, 0, 0, 0, 0, 0);
}
static bool env_or_skip(const char *env)
{
if (!getenv(env)) {
report_skip("missing %s environment variable", env);
return false;
}
return true;
}
static void gen_report(struct sbiret *ret,
long expected_error, long expected_value)
{
bool check_error = ret->error == expected_error;
bool check_value = ret->value == expected_value;
if (!check_error || !check_value)
report_info("expected (error: %ld, value: %ld), received: (error: %ld, value %ld)",
expected_error, expected_value, ret->error, ret->value);
report(check_error, "expected sbi.error");
report(check_value, "expected sbi.value");
}
static void check_base(void)
{
struct sbiret ret;
long expected;
report_prefix_push("base");
ret = __base_sbi_ecall(SBI_EXT_BASE_GET_SPEC_VERSION, 0);
if (ret.error || ret.value < 2) {
report_skip("SBI spec version 0.2 or higher required");
return;
}
report_prefix_push("spec_version");
if (env_or_skip("SPEC_VERSION")) {
expected = strtol(getenv("SPEC_VERSION"), NULL, 0);
gen_report(&ret, 0, expected);
}
report_prefix_pop();
report_prefix_push("impl_id");
if (env_or_skip("IMPL_ID")) {
expected = strtol(getenv("IMPL_ID"), NULL, 0);
ret = __base_sbi_ecall(SBI_EXT_BASE_GET_IMP_ID, 0);
gen_report(&ret, 0, expected);
}
report_prefix_pop();
report_prefix_push("probe_ext");
expected = getenv("PROBE_EXT") ? strtol(getenv("PROBE_EXT"), NULL, 0) : 1;
ret = __base_sbi_ecall(SBI_EXT_BASE_PROBE_EXT, SBI_EXT_BASE);
gen_report(&ret, 0, expected);
report_prefix_pop();
report_prefix_push("mvendorid");
if (env_or_skip("MVENDORID")) {
expected = strtol(getenv("MVENDORID"), NULL, 0);
ret = __base_sbi_ecall(SBI_EXT_BASE_GET_MVENDORID, 0);
gen_report(&ret, 0, expected);
}
report_prefix_pop();
report_prefix_push("marchid");
if (env_or_skip("MARCHID")) {
expected = strtol(getenv("MARCHID"), NULL, 0);
ret = __base_sbi_ecall(SBI_EXT_BASE_GET_MARCHID, 0);
gen_report(&ret, 0, expected);
}
report_prefix_pop();
report_prefix_pop();
}
int main(int argc, char **argv)
{
if (argc > 1 && !strcmp(argv[1], "-h")) {
help();
exit(0);
}
report_prefix_push("sbi");
check_base();
return report_summary();
}