Skip to content

Commit 5a32dc8

Browse files
authored
Merge pull request #300 from tactcomplabs/extension_versions
Add support for extension versions
2 parents 51ff62c + 93c8eaa commit 5a32dc8

File tree

6 files changed

+115
-30
lines changed

6 files changed

+115
-30
lines changed

include/RevFeature.h

Lines changed: 13 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -23,22 +23,25 @@ namespace SST::RevCPU {
2323
/// ORed to indicate multiple extensions being present.
2424
enum RevFeatureType : uint32_t {
2525
RV_UNKNOWN = 0, ///< RevFeatureType: unknown feature
26-
RV_E = 1 << 0, ///< RevFeatureType: E-extension
27-
RV_I = 1 << 1, ///< RevFeatureType: I-extension
26+
RV_I = 1 << 0, ///< RevFeatureType: I-extension
27+
RV_E = 1 << 1, ///< RevFeatureType: E-extension
2828
RV_M = 1 << 2, ///< RevFeatureType: M-extension
2929
RV_A = 1 << 3, ///< RevFeatureType: A-extension
3030
RV_F = 1 << 4, ///< RevFeatureType: F-extension
3131
RV_D = 1 << 5, ///< RevFeatureType: D-extension
3232
RV_Q = 1 << 6, ///< RevFeatureType: Q-extension
3333
RV_C = 1 << 7, ///< RevFeatureType: C-extension
34-
RV_P = 1 << 8, ///< RevFeatureType: P-Extension
35-
RV_V = 1 << 9, ///< RevFeatureType: V-extension
36-
RV_H = 1 << 10, ///< RevFeatureType: H-extension
37-
RV_ZICSR = 1 << 11, ///< RevFEatureType: Zicsr-extension
38-
RV_ZIFENCEI = 1 << 12, ///< RevFeatureType: Zifencei-extension
39-
RV_ZTSO = 1 << 13, ///< RevFeatureType: Ztso-extension
40-
RV_ZFA = 1 << 14, ///< RevFeatureType: Zfa-extension
41-
RV_ZICBOM = 1 << 15, ///< RevFeatureType: Zicbom-extension
34+
RV_B = 1 << 8, ///< RevFeatureType: C-extension
35+
RV_P = 1 << 9, ///< RevFeatureType: P-Extension
36+
RV_V = 1 << 10, ///< RevFeatureType: V-extension
37+
RV_H = 1 << 11, ///< RevFeatureType: H-extension
38+
RV_ZICBOM = 1 << 12, ///< RevFeatureType: Zicbom-extension
39+
RV_ZICSR = 1 << 13, ///< RevFEatureType: Zicsr-extension
40+
RV_ZIFENCEI = 1 << 14, ///< RevFeatureType: Zifencei-extension
41+
RV_ZFA = 1 << 15, ///< RevFeatureType: Zfa-extension
42+
RV_ZFH = 1 << 16, ///< RevFeatureType: H-extension
43+
RV_ZFHMIN = 1 << 17, ///< RevFeatureRtpe: Zfhmin extension
44+
RV_ZTSO = 1 << 18, ///< RevFeatureType: Ztso-extension
4245
};
4346

4447
class RevFeature {

src/RevFeature.cc

Lines changed: 48 additions & 20 deletions
Original file line numberDiff line numberDiff line change
@@ -9,6 +9,7 @@
99
//
1010

1111
#include "RevFeature.h"
12+
#include <cctype>
1213
#include <cstring>
1314
#include <string_view>
1415
#include <utility>
@@ -39,39 +40,48 @@ bool RevFeature::ParseMachineModel() {
3940
output->verbose( CALL_INFO, 6, 0, "Core %u ; Setting XLEN to %u\n", ProcID, xlen );
4041
output->verbose( CALL_INFO, 6, 0, "Core %u ; Architecture string=%s\n", ProcID, mac );
4142

43+
// clang-format off
4244
///< List of architecture extensions. These must listed in canonical order
4345
///< as shown in Table 27.11, Chapter 27, of the RISC-V Unprivileged Spec
4446
///< (Table 74 of Chapter 36 in the 2024 version).
4547
///<
4648
///< By using a canonical ordering, the extensions' presence can be tested
4749
///< in linear time complexity of the table and the string. Some of the
4850
///< extensions imply other extensions, so the extension flags are ORed.
49-
// clang-format off
50-
static constexpr std::pair<std::string_view, uint32_t> table[] = {
51-
{ "I", RV_I },
52-
{ "E", RV_E },
53-
{ "M", RV_M },
54-
{ "A", RV_A },
55-
{ "F", RV_F | RV_ZICSR },
56-
{ "D", RV_D | RV_F | RV_ZICSR },
57-
{ "G", RV_I | RV_M | RV_A | RV_F | RV_D | RV_ZICSR | RV_ZIFENCEI },
58-
{ "Q", RV_Q | RV_D | RV_F | RV_ZICSR },
59-
{ "C", RV_C },
60-
{ "P", RV_P },
61-
{ "V", RV_V | RV_D | RV_F | RV_ZICSR },
62-
{ "H", RV_H },
63-
{ "Zicsr", RV_ZICSR },
64-
{ "Zifencei", RV_ZIFENCEI },
65-
{ "Ztso", RV_ZTSO },
66-
{ "Zfa", RV_ZFA | RV_F | RV_ZICSR },
67-
{ "Zicbom", RV_ZICBOM },
51+
///<
52+
///< The second and third values are the major and minor default version.
53+
///< The fourth and fifth values are the major version range that Rev supports.
54+
///< Values of -1, 0 for the fourth and fifth values indicates no Rev support yet.
55+
///<
56+
///< ExtensionName DefaultMajor DefaultMinor MinSupportedVersion MaxSupportedVersion Flags
57+
static constexpr std::tuple<std::string_view, uint32_t, uint32_t, uint32_t, uint32_t, uint32_t> table[] = {
58+
{ "I", 2, 1, 2, 2, RV_I },
59+
{ "E", 2, 0, -1, 0, RV_E }, // Unsupported
60+
{ "M", 2, 0, 2, 2, RV_M },
61+
{ "A", 2, 1, 2, 2, RV_A },
62+
{ "F", 2, 2, 2, 2, RV_F | RV_ZICSR },
63+
{ "D", 2, 2, 2, 2, RV_D | RV_F | RV_ZICSR },
64+
{ "G", 2, 0, 2, 2, RV_I | RV_M | RV_A | RV_F | RV_D | RV_ZICSR | RV_ZIFENCEI },
65+
{ "Q", 2, 2, -1, 0, RV_Q | RV_D | RV_F | RV_ZICSR }, // Unsupported
66+
{ "C", 2, 0, 2, 2, RV_C },
67+
{ "B", 1, 0, -1, 0, RV_B }, // Unsupported
68+
{ "P", 0, 2, -1, 0, RV_P }, // Unsupported
69+
{ "V", 1, 0, -1, 0, RV_V | RV_D | RV_F | RV_ZICSR },
70+
{ "H", 1, 0, -1, 0, RV_H }, // Unsupported
71+
{ "Zicbom", 1, 0, 1, 1, RV_ZICBOM },
72+
{ "Zicsr", 2, 0, 2, 2, RV_ZICSR },
73+
{ "Zifencei", 2, 0, 2, 2, RV_ZIFENCEI },
74+
{ "Zfa", 1, 0, -1, 0, RV_ZFA | RV_F | RV_ZICSR }, // Unsupported
75+
{ "Zfh", 1, 0, -1, 0, RV_ZFH | RV_ZFHMIN | RV_F | RV_ZICSR }, // Unsupported
76+
{ "Zfhmin", 1, 0, -1, 0, RV_ZFHMIN | RV_F | RV_ZICSR }, // Unsupported
77+
{ "Ztso", 1, 0, -1, 0, RV_ZTSO }, // Unsupported
6878
};
6979
// clang-format on
7080

7181
// -- step 2: parse all the features
7282
// Note: Extension strings, if present, must appear in the order listed in the table above.
7383
if( *mac ) {
74-
for( const auto& [ext, flags] : table ) {
84+
for( auto [ext, majorVersion, minorVersion, minimumVersion, maximumVersion, flags] : table ) {
7585
// Look for an architecture string matching the current extension
7686
if( !strncasecmp( mac, ext.data(), ext.size() ) ) {
7787

@@ -81,6 +91,24 @@ bool RevFeature::ParseMachineModel() {
8191
// Move past the currently matching extension
8292
mac += ext.size();
8393

94+
// Optional version string follows extension
95+
if( isdigit( *mac ) ) {
96+
majorVersion = strtoul( mac, const_cast<char**>( &mac ), 10 );
97+
if( tolower( *mac ) == 'p' && isdigit( *++mac ) )
98+
minorVersion = strtoul( mac, const_cast<char**>( &mac ), 10 );
99+
}
100+
101+
if( majorVersion < minimumVersion || majorVersion > maximumVersion ) {
102+
output->fatal(
103+
CALL_INFO,
104+
-1,
105+
"Error: Version %" PRIu32 ".%" PRIu32 " of %s extension is not supported\n",
106+
majorVersion,
107+
minorVersion,
108+
ext.data()
109+
);
110+
}
111+
84112
// Skip underscore separators
85113
while( *mac == '_' )
86114
++mac;

test/CMakeLists.txt

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -204,6 +204,7 @@ endif()
204204
endmacro()
205205

206206
# add_rev_test(test_name test_dir timeout labels)
207+
add_rev_test(EXT_VERSION ext_version 20 "rv64")
207208
add_rev_test(EX1 ex1 30 "memh;rv32")
208209
add_rev_test(EX2 ex2 30 "memh;rv64")
209210
add_rev_test(EX3 ex3 30 "memh;rv32")

test/ext_version/Makefile

Lines changed: 25 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,25 @@
1+
#
2+
# Makefile
3+
#
4+
# makefile: ext_version
5+
#
6+
# Copyright (C) 2017-2024 Tactical Computing Laboratories, LLC
7+
# All Rights Reserved
8+
9+
#
10+
# See LICENSE in the top level directory for licensing details
11+
#
12+
13+
.PHONY: src
14+
15+
EXAMPLE=ext_version
16+
CC=${RVCC}
17+
ARCH=rv64imafdc
18+
19+
all: $(EXAMPLE).exe
20+
$(EXAMPLE).exe: $(EXAMPLE).c
21+
$(CC) -march=$(ARCH) -O3 -static -o $(EXAMPLE).exe $(EXAMPLE).c
22+
clean:
23+
rm -Rf $(EXAMPLE).exe
24+
25+
#-- EOF

test/ext_version/ext_version.c

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,3 @@
1+
int main( void ) {
2+
return 0;
3+
}

test/ext_version/run_ext_version.sh

Lines changed: 25 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,25 @@
1+
#!/bin/sh
2+
set -e
3+
4+
make clean
5+
make
6+
7+
# Unknown extension
8+
sst --add-lib-path=../../build/src/ ../rev-model-options-config.py -- --program "ext_version.exe" --args "one" --enableMemH=0 --machine="[CORES:RV64XGC]" 2>&1 | grep -q 'Error: failed to parse the machine model: RV64XGC'
9+
10+
# Out of order extension
11+
sst --add-lib-path=../../build/src/ ../rev-model-options-config.py -- --program "ext_version.exe" --args "one" --enableMemH=0 --machine="[CORES:RV64GVC]" 2>&1 | grep -q 'Error: failed to parse the machine model: RV64GVC'
12+
13+
# Incomplete version string
14+
sst --add-lib-path=../../build/src/ ../rev-model-options-config.py -- --program "ext_version.exe" --args "one" --enableMemH=0 --machine="[CORES:RV64XGC2P]" 2>&1 | grep -q 'Error: failed to parse the machine model: RV64XGC2P'
15+
16+
# Unsupported version
17+
sst --add-lib-path=../../build/src/ ../rev-model-options-config.py -- --program "ext_version.exe" --args "one" --enableMemH=0 --machine="[CORES:RV64GCV0p7]" 2>&1 | grep -q 'Error: Version 0.7 of V extension is not supported'
18+
19+
# Supported version
20+
sst --add-lib-path=../../build/src/ ../rev-model-options-config.py -- --program "ext_version.exe" --args "one" --enableMemH=0 --machine="[CORES:rv64i2p0m2a2p0fd2p0c]" 2>&1 | grep -q 'Simulation is complete'
21+
22+
# Supported version
23+
sst --add-lib-path=../../build/src/ ../rev-model-options-config.py -- --program "ext_version.exe" --args "one" --enableMemH=0 --machine="[CORES:rv64i2p0m2a2p0fd2p0c2_p]" 2>&1 | grep -q 'Simulation is complete'
24+
25+
echo 'Simulation is complete'

0 commit comments

Comments
 (0)