1 // SPDX-License-Identifier: GPL-2.0-only 2 /* 3 * SBI verification 4 * 5 * Copyright (C) 2023, Ventana Micro Systems Inc., Andrew Jones <ajones@ventanamicro.com> 6 */ 7 #include <libcflat.h> 8 #include <stdlib.h> 9 #include <asm/sbi.h> 10 11 static void help(void) 12 { 13 puts("Test SBI\n"); 14 puts("An environ must be provided where expected values are given.\n"); 15 } 16 17 static struct sbiret __base_sbi_ecall(int fid, unsigned long arg0) 18 { 19 return sbi_ecall(SBI_EXT_BASE, fid, arg0, 0, 0, 0, 0, 0); 20 } 21 22 static bool env_or_skip(const char *env) 23 { 24 if (!getenv(env)) { 25 report_skip("missing %s environment variable", env); 26 return false; 27 } 28 29 return true; 30 } 31 32 static void gen_report(struct sbiret *ret, 33 long expected_error, long expected_value) 34 { 35 bool check_error = ret->error == expected_error; 36 bool check_value = ret->value == expected_value; 37 38 if (!check_error || !check_value) 39 report_info("expected (error: %ld, value: %ld), received: (error: %ld, value %ld)", 40 expected_error, expected_value, ret->error, ret->value); 41 42 report(check_error, "expected sbi.error"); 43 report(check_value, "expected sbi.value"); 44 } 45 46 static void check_base(void) 47 { 48 struct sbiret ret; 49 long expected; 50 51 report_prefix_push("base"); 52 53 ret = __base_sbi_ecall(SBI_EXT_BASE_GET_SPEC_VERSION, 0); 54 if (ret.error || ret.value < 2) { 55 report_skip("SBI spec version 0.2 or higher required"); 56 return; 57 } 58 59 report_prefix_push("spec_version"); 60 if (env_or_skip("SPEC_VERSION")) { 61 expected = strtol(getenv("SPEC_VERSION"), NULL, 0); 62 gen_report(&ret, 0, expected); 63 } 64 report_prefix_pop(); 65 66 report_prefix_push("impl_id"); 67 if (env_or_skip("IMPL_ID")) { 68 expected = strtol(getenv("IMPL_ID"), NULL, 0); 69 ret = __base_sbi_ecall(SBI_EXT_BASE_GET_IMP_ID, 0); 70 gen_report(&ret, 0, expected); 71 } 72 report_prefix_pop(); 73 74 report_prefix_push("impl_version"); 75 if (env_or_skip("IMPL_VERSION")) { 76 expected = strtol(getenv("IMPL_VERSION"), NULL, 0); 77 ret = __base_sbi_ecall(SBI_EXT_BASE_GET_IMP_VERSION, 0); 78 gen_report(&ret, 0, expected); 79 } 80 report_prefix_pop(); 81 82 report_prefix_push("probe_ext"); 83 expected = getenv("PROBE_EXT") ? strtol(getenv("PROBE_EXT"), NULL, 0) : 1; 84 ret = __base_sbi_ecall(SBI_EXT_BASE_PROBE_EXT, SBI_EXT_BASE); 85 gen_report(&ret, 0, expected); 86 report_prefix_pop(); 87 88 report_prefix_push("mvendorid"); 89 if (env_or_skip("MVENDORID")) { 90 expected = strtol(getenv("MVENDORID"), NULL, 0); 91 ret = __base_sbi_ecall(SBI_EXT_BASE_GET_MVENDORID, 0); 92 gen_report(&ret, 0, expected); 93 } 94 report_prefix_pop(); 95 96 report_prefix_push("marchid"); 97 if (env_or_skip("MARCHID")) { 98 expected = strtol(getenv("MARCHID"), NULL, 0); 99 ret = __base_sbi_ecall(SBI_EXT_BASE_GET_MARCHID, 0); 100 gen_report(&ret, 0, expected); 101 } 102 report_prefix_pop(); 103 104 report_prefix_push("mimpid"); 105 if (env_or_skip("MIMPID")) { 106 expected = strtol(getenv("MIMPID"), NULL, 0); 107 ret = __base_sbi_ecall(SBI_EXT_BASE_GET_MIMPID, 0); 108 gen_report(&ret, 0, expected); 109 } 110 report_prefix_pop(); 111 112 report_prefix_pop(); 113 } 114 115 int main(int argc, char **argv) 116 { 117 118 if (argc > 1 && !strcmp(argv[1], "-h")) { 119 help(); 120 exit(0); 121 } 122 123 report_prefix_push("sbi"); 124 check_base(); 125 126 return report_summary(); 127 } 128