@@ -140,6 +140,16 @@ function clause write_CSR(0x301, value) = { misa = legalize_misa(misa, value); m
140
140
function clause currentlyEnabled (Ext_U ) = hartSupports (Ext_U ) & misa [U ] == 0b1
141
141
function clause currentlyEnabled (Ext_S ) = hartSupports (Ext_S ) & misa [S ] == 0b1
142
142
143
+ function clause currentlyEnabled (Ext_Svbare ) = currentlyEnabled (Ext_S )
144
+ function clause currentlyEnabled (Ext_Sv32 ) = hartSupports (Ext_Sv32 ) & currentlyEnabled (Ext_S )
145
+ function clause currentlyEnabled (Ext_Sv39 ) = hartSupports (Ext_Sv39 ) & currentlyEnabled (Ext_S )
146
+ function clause currentlyEnabled (Ext_Sv48 ) = hartSupports (Ext_Sv48 ) & currentlyEnabled (Ext_S )
147
+ function clause currentlyEnabled (Ext_Sv57 ) = hartSupports (Ext_Sv57 ) & currentlyEnabled (Ext_S )
148
+
149
+ function virtual_memory_supported () -> bool = {
150
+ currentlyEnabled (Ext_Sv32 ) | currentlyEnabled (Ext_Sv39 ) | currentlyEnabled (Ext_Sv48 ) | currentlyEnabled (Ext_Sv57 )
151
+ }
152
+
143
153
/*
144
154
* Illegal values legalized to least privileged mode supported.
145
155
* Note: the only valid combinations of supported modes are M, M+U, M+S+U.
@@ -235,7 +245,7 @@ function legalize_mstatus(o : Mstatus, v : bits(64)) -> Mstatus = {
235
245
TW = if currentlyEnabled (Ext_U ) then v [TW ] else 0b0 ,
236
246
TVM = if currentlyEnabled (Ext_S ) then v [TVM ] else 0b0 ,
237
247
MXR = if currentlyEnabled (Ext_S ) then v [MXR ] else 0b0 ,
238
- SUM = if currentlyEnabled ( Ext_S ) then v [SUM ] else 0b0 , // TODO: Should also be disabled if satp.MODE is read-only 0
248
+ SUM = if virtual_memory_supported ( ) then v [SUM ] else 0b0 ,
239
249
MPRV = if currentlyEnabled (Ext_U ) then v [MPRV ] else 0b0 ,
240
250
/* We don't have any extension context yet. */
241
251
XS = extStatus_to_bits (Off ),
@@ -851,13 +861,26 @@ function legalize_satp(
851
861
written_value : xlenbits ,
852
862
) -> xlenbits = {
853
863
if xlen == 32 then {
854
- /* all 32-bit satp modes are valid */
855
- written_value
864
+ let s = Mk_Satp32 (written_value );
865
+ match satpMode_of_bits (arch , 0b000 @ s [Mode ]) {
866
+ None () => prev_value ,
867
+ Some (Sv_mode ) => match Sv_mode {
868
+ Bare if currentlyEnabled (Ext_Svbare ) => s . bits ,
869
+ Sv32 if currentlyEnabled (Ext_Sv32 ) => s . bits ,
870
+ _ => prev_value ,
871
+ }
872
+ }
856
873
} else if xlen == 64 then {
857
874
let s = Mk_Satp64 (written_value );
858
875
match satpMode_of_bits (arch , s [Mode ]) {
859
876
None () => prev_value ,
860
- Some (_ ) => s . bits
877
+ Some (Sv_mode ) => match Sv_mode {
878
+ Bare if currentlyEnabled (Ext_Svbare ) => s . bits ,
879
+ Sv39 if currentlyEnabled (Ext_Sv39 ) => s . bits ,
880
+ Sv48 if currentlyEnabled (Ext_Sv48 ) => s . bits ,
881
+ Sv57 if currentlyEnabled (Ext_Sv57 ) => s . bits ,
882
+ _ => prev_value ,
883
+ }
861
884
}
862
885
} else {
863
886
internal_error (__FILE__, __LINE__, "Unsupported xlen" ^ dec_str (xlen ))
0 commit comments