From 9a578d3670866840e51845d32ff523297d707a6a Mon Sep 17 00:00:00 2001 From: Dr-Noob Date: Sun, 29 Oct 2023 17:14:47 +0000 Subject: [PATCH] [v1.04][RISCV] Make single-letter extension detection more robust. s and u are invalid but might appear (#200), so just skip them --- src/riscv/riscv.c | 30 ++++++++++++++++++++++++++++-- src/riscv/riscv.h | 1 - 2 files changed, 28 insertions(+), 3 deletions(-) diff --git a/src/riscv/riscv.c b/src/riscv/riscv.c index 6c1624d..af43066 100644 --- a/src/riscv/riscv.c +++ b/src/riscv/riscv.c @@ -78,6 +78,18 @@ int parse_multi_letter_extension(struct extensions* ext, char* e) { return multi_letter_extension_len; } +bool valid_extension(char ext) { + bool found = false; + uint64_t idx = 0; + + while(idx < sizeof(extension_list)/sizeof(extension_list[0]) && !found) { + found = (extension_list[idx].id == (ext - 'a')); + if(!found) idx++; + } + + return found; +} + struct extensions* get_extensions_from_str(char* str) { struct extensions* ext = emalloc(sizeof(struct extensions)); ext->mask = 0; @@ -114,8 +126,22 @@ struct extensions* get_extensions_from_str(char* str) { e += multi_letter_extension_len; } else { - int n = *e - 'a'; - ext->mask |= 1UL << n; + // Single-letter extensions 's' and 'u' are invalid + // according to Linux kernel (arch/riscv/kernel/cpufeature.c: + // riscv_fill_hwcap). Optionally, we could opt for using + // hwcap instead of cpuinfo to avoid this + if (*e == 's' || *e == 'u') { + continue; + } + // Make sure that the extension is valid before + // adding it to the mask + if(valid_extension(*e)) { + int n = *e - 'a'; + ext->mask |= 1UL << n; + } + else { + printBug("get_extensions_from_str: Invalid extension: '%c'", *e); + } } } diff --git a/src/riscv/riscv.h b/src/riscv/riscv.h index d6bc9b2..f9d3d61 100644 --- a/src/riscv/riscv.h +++ b/src/riscv/riscv.h @@ -54,7 +54,6 @@ static const struct extension extension_list[] = { { 'v' - 'a', "(V) Vector Operations" }, { 'n' - 'a', "(N) User-Level Interrupts" }, { 'h' - 'a', "(H) Hypervisor" }, - { 's' - 'a', "(S) Supervisor-level Instructions" }, // multi-letter extensions { RISCV_ISA_EXT_SSCOFPMF, "(Sscofpmf) Count OverFlow and Privilege Mode Filtering" }, { RISCV_ISA_EXT_SSTC, "(Sstc) S and VS level Time Compare" },