31: Add more CSRs r=laanwj a=Disasm



Co-authored-by: Vadim Kaushan <admin@disasm.info>
This commit is contained in:
bors[bot] 2019-07-23 17:41:40 +00:00
commit 7f1e4a56cf
28 changed files with 663 additions and 72 deletions

View File

@ -1,6 +1,6 @@
[package]
name = "riscv"
version = "0.5.3"
version = "0.5.4"
repository = "https://github.com/rust-embedded/riscv"
authors = ["The RISC-V Team <risc-v@teams.rust-embedded.org>"]
categories = ["embedded", "hardware-support", "no-std"]

277
asm.S
View File

@ -24,37 +24,252 @@ __sfence_vma:
sfence.vma a0, a1
ret
REG_READ_WRITE(fcsr, 0x003)
REG_SET_CLEAR(fcsr, 0x003)
// User Trap Setup
RW(0x000, ustatus) // User status register
RW(0x004, uie) // User interrupt-enable register
RW(0x005, utvec) // User trap handler base address
// M-mode registers
REG_READ(mcause, 0x342)
REG_READ(mcycle, 0xB00)
REG_READ(mepc, 0x341)
REG_READ(mie, 0x304)
REG_SET_CLEAR(mie, 0x304)
REG_READ(minstret, 0xB02)
REG_READ(mip, 0x344)
REG_READ(misa, 0x301)
REG_READ_WRITE(mstatus, 0x300)
REG_SET_CLEAR(mstatus, 0x300)
REG_READ_WRITE(mtvec, 0x305)
REG_READ(mvendorid, 0xF11)
REG_READ(marchid, 0xF12)
REG_READ(mimpid, 0xF13)
REG_READ(mhartid, 0xF14)
// User Trap Handling
RW(0x040, uscratch) // Scratch register for user trap handlers
RW(0x041, uepc) // User exception program counter
RW(0x042, ucause) // User trap cause
RW(0x043, utval) // User bad address or instruction
RW(0x044, uip) // User interrupt pending
// S-mode registers
REG_READ_WRITE(satp, 0x180)
REG_READ(scause, 0x142)
REG_READ_WRITE(sepc, 0x141)
REG_READ(sie, 0x104)
REG_SET_CLEAR(sie, 0x104)
REG_READ(sip, 0x144)
REG_READ_WRITE(sscratch, 0x140)
REG_READ_WRITE(sstatus, 0x100)
REG_SET_CLEAR(sstatus, 0x100)
REG_READ(stval, 0x143)
REG_READ_WRITE(stvec, 0x105)
// User Floating-Point CSRs
RW(0x001, fflags) // Floating-Point Accrued Exceptions
RW(0x002, frm) // Floating-Point Dynamic Rounding Mode
RW(0x003, fcsr) // Floating-Point Control and Status Register (frm + fflags)
REG_READ(time, 0xC01)
// User Counter/Timers
RO( 0xC00, cycle) // Cycle counter for RDCYCLE instruction
RO( 0xC01, time) // Timer for RDTIME instruction
RO( 0xC02, instret) // Instructions-retired counter for RDINSTRET instruction
RO( 0xC03, hpmcounter3) // Performance-monitoring counter
RO( 0xC04, hpmcounter4) // Performance-monitoring counter
RO( 0xC05, hpmcounter5) // Performance-monitoring counter
RO( 0xC06, hpmcounter6) // Performance-monitoring counter
RO( 0xC07, hpmcounter7) // Performance-monitoring counter
RO( 0xC08, hpmcounter8) // Performance-monitoring counter
RO( 0xC09, hpmcounter9) // Performance-monitoring counter
RO( 0xC0A, hpmcounter10) // Performance-monitoring counter
RO( 0xC0B, hpmcounter11) // Performance-monitoring counter
RO( 0xC0C, hpmcounter12) // Performance-monitoring counter
RO( 0xC0D, hpmcounter13) // Performance-monitoring counter
RO( 0xC0E, hpmcounter14) // Performance-monitoring counter
RO( 0xC0F, hpmcounter15) // Performance-monitoring counter
RO( 0xC10, hpmcounter16) // Performance-monitoring counter
RO( 0xC11, hpmcounter17) // Performance-monitoring counter
RO( 0xC12, hpmcounter18) // Performance-monitoring counter
RO( 0xC13, hpmcounter19) // Performance-monitoring counter
RO( 0xC14, hpmcounter20) // Performance-monitoring counter
RO( 0xC15, hpmcounter21) // Performance-monitoring counter
RO( 0xC16, hpmcounter22) // Performance-monitoring counter
RO( 0xC17, hpmcounter23) // Performance-monitoring counter
RO( 0xC18, hpmcounter24) // Performance-monitoring counter
RO( 0xC19, hpmcounter25) // Performance-monitoring counter
RO( 0xC1A, hpmcounter26) // Performance-monitoring counter
RO( 0xC1B, hpmcounter27) // Performance-monitoring counter
RO( 0xC1C, hpmcounter28) // Performance-monitoring counter
RO( 0xC1D, hpmcounter29) // Performance-monitoring counter
RO( 0xC1E, hpmcounter30) // Performance-monitoring counter
RO( 0xC1F, hpmcounter31) // Performance-monitoring counter
RO32(0xC80, cycleh) // Upper 32 bits of cycle, RV32I only
RO32(0xC81, timeh) // Upper 32 bits of time, RV32I only
RO32(0xC82, instreth) // Upper 32 bits of instret, RV32I only
RO32(0xC83, hpmcounter3h) // Upper 32 bits of hpmcounter3, RV32I only
RO32(0xC84, hpmcounter4h)
RO32(0xC85, hpmcounter5h)
RO32(0xC86, hpmcounter6h)
RO32(0xC87, hpmcounter7h)
RO32(0xC88, hpmcounter8h)
RO32(0xC89, hpmcounter9h)
RO32(0xC8A, hpmcounter10h)
RO32(0xC8B, hpmcounter11h)
RO32(0xC8C, hpmcounter12h)
RO32(0xC8D, hpmcounter13h)
RO32(0xC8E, hpmcounter14h)
RO32(0xC8F, hpmcounter15h)
RO32(0xC90, hpmcounter16h)
RO32(0xC91, hpmcounter17h)
RO32(0xC92, hpmcounter18h)
RO32(0xC93, hpmcounter19h)
RO32(0xC94, hpmcounter20h)
RO32(0xC95, hpmcounter21h)
RO32(0xC96, hpmcounter22h)
RO32(0xC97, hpmcounter23h)
RO32(0xC98, hpmcounter24h)
RO32(0xC99, hpmcounter25h)
RO32(0xC9A, hpmcounter26h)
RO32(0xC9B, hpmcounter27h)
RO32(0xC9C, hpmcounter28h)
RO32(0xC9D, hpmcounter29h)
RO32(0xC9E, hpmcounter30h)
RO32(0xC9F, hpmcounter31h)
// Supervisor Trap Setup
RW(0x100, sstatus) // Supervisor status register
RW(0x102, sedeleg) // Supervisor exception delegation register
RW(0x103, sideleg) // Supervisor interrupt delegation register
RW(0x104, sie) // Supervisor interrupt-enable register
RW(0x105, stvec) // Supervisor trap handler base address
RW(0x106, scounteren) // Supervisor counter enable
// Supervisor Trap Handling
RW(0x140, sscratch) // Scratch register for supervisor trap handlers
RW(0x141, sepc) // Supervisor exception program counter
RW(0x142, scause) // Supervisor trap cause
RW(0x143, stval) // Supervisor bad address or instruction
RW(0x144, sip) // Supervisor interrupt pending
// Supervisor Protection and Translation
RW(0x180, satp) // Supervisor address translation and protection
// Machine Information Registers
RO(0xF11, mvendorid) // Vendor ID
RO(0xF12, marchid) // Architecture ID
RO(0xF13, mimpid) // Implementation ID
RO(0xF14, mhartid) // Hardware thread ID
// Machine Trap Setup
RW(0x300, mstatus) // Machine status register
RW(0x301, misa) // ISA and extensions
RW(0x302, medeleg) // Machine exception delegation register
RW(0x303, mideleg) // Machine interrupt delegation register
RW(0x304, mie) // Machine interrupt-enable register
RW(0x305, mtvec) // Machine trap handler base address
RW(0x306, mcounteren) // Machine counter enable
// Machine Trap Handling
RW(0x340, mscratch) // Scratch register for machine trap handlers
RW(0x341, mepc) // Machine exception program counter
RW(0x342, mcause) // Machine trap cause
RW(0x343, mtval) // Machine bad address or instruction
RW(0x344, mip) // Machine interrupt pending
// Machine Protection and Translation
RW( 0x3A0, pmpcfg0) // Physical memory protection configuration
RW32(0x3A1, pmpcfg1) // Physical memory protection configuration, RV32 only
RW( 0x3A2, pmpcfg2) // Physical memory protection configuration
RW32(0x3A3, pmpcfg3) // Physical memory protection configuration, RV32 only
RW( 0x3B0, pmpaddr0) // Physical memory protection address register
RW( 0x3B1, pmpaddr1) // Physical memory protection address register
RW( 0x3B2, pmpaddr2) // Physical memory protection address register
RW( 0x3B3, pmpaddr3) // Physical memory protection address register
RW( 0x3B4, pmpaddr4) // Physical memory protection address register
RW( 0x3B5, pmpaddr5) // Physical memory protection address register
RW( 0x3B6, pmpaddr6) // Physical memory protection address register
RW( 0x3B7, pmpaddr7) // Physical memory protection address register
RW( 0x3B8, pmpaddr8) // Physical memory protection address register
RW( 0x3B9, pmpaddr9) // Physical memory protection address register
RW( 0x3BA, pmpaddr10) // Physical memory protection address register
RW( 0x3BB, pmpaddr11) // Physical memory protection address register
RW( 0x3BC, pmpaddr12) // Physical memory protection address register
RW( 0x3BD, pmpaddr13) // Physical memory protection address register
RW( 0x3BE, pmpaddr14) // Physical memory protection address register
RW( 0x3BF, pmpaddr15) // Physical memory protection address register
// Machine Counter/Timers
RO( 0xB00, mcycle) // Machine cycle counter
RO( 0xB02, minstret) // Machine instructions-retired counter
RO( 0xB03, mhpmcounter3) // Machine performance-monitoring counter
RO( 0xB04, mhpmcounter4) // Machine performance-monitoring counter
RO( 0xB05, mhpmcounter5) // Machine performance-monitoring counter
RO( 0xB06, mhpmcounter6) // Machine performance-monitoring counter
RO( 0xB07, mhpmcounter7) // Machine performance-monitoring counter
RO( 0xB08, mhpmcounter8) // Machine performance-monitoring counter
RO( 0xB09, mhpmcounter9) // Machine performance-monitoring counter
RO( 0xB0A, mhpmcounter10) // Machine performance-monitoring counter
RO( 0xB0B, mhpmcounter11) // Machine performance-monitoring counter
RO( 0xB0C, mhpmcounter12) // Machine performance-monitoring counter
RO( 0xB0D, mhpmcounter13) // Machine performance-monitoring counter
RO( 0xB0E, mhpmcounter14) // Machine performance-monitoring counter
RO( 0xB0F, mhpmcounter15) // Machine performance-monitoring counter
RO( 0xB10, mhpmcounter16) // Machine performance-monitoring counter
RO( 0xB11, mhpmcounter17) // Machine performance-monitoring counter
RO( 0xB12, mhpmcounter18) // Machine performance-monitoring counter
RO( 0xB13, mhpmcounter19) // Machine performance-monitoring counter
RO( 0xB14, mhpmcounter20) // Machine performance-monitoring counter
RO( 0xB15, mhpmcounter21) // Machine performance-monitoring counter
RO( 0xB16, mhpmcounter22) // Machine performance-monitoring counter
RO( 0xB17, mhpmcounter23) // Machine performance-monitoring counter
RO( 0xB18, mhpmcounter24) // Machine performance-monitoring counter
RO( 0xB19, mhpmcounter25) // Machine performance-monitoring counter
RO( 0xB1A, mhpmcounter26) // Machine performance-monitoring counter
RO( 0xB1B, mhpmcounter27) // Machine performance-monitoring counter
RO( 0xB1C, mhpmcounter28) // Machine performance-monitoring counter
RO( 0xB1D, mhpmcounter29) // Machine performance-monitoring counter
RO( 0xB1E, mhpmcounter30) // Machine performance-monitoring counter
RO( 0xB1F, mhpmcounter31) // Machine performance-monitoring counter
RO32(0xB80, mcycleh) // Upper 32 bits of mcycle, RV32I only
RO32(0xB82, minstreth) // Upper 32 bits of minstret, RV32I only
RO32(0xB83, mhpmcounter3h) // Upper 32 bits of mhpmcounter3, RV32I only
RO32(0xB84, mhpmcounter4h)
RO32(0xB85, mhpmcounter5h)
RO32(0xB86, mhpmcounter6h)
RO32(0xB87, mhpmcounter7h)
RO32(0xB88, mhpmcounter8h)
RO32(0xB89, mhpmcounter9h)
RO32(0xB8A, mhpmcounter10h)
RO32(0xB8B, mhpmcounter11h)
RO32(0xB8C, mhpmcounter12h)
RO32(0xB8D, mhpmcounter13h)
RO32(0xB8E, mhpmcounter14h)
RO32(0xB8F, mhpmcounter15h)
RO32(0xB90, mhpmcounter16h)
RO32(0xB91, mhpmcounter17h)
RO32(0xB92, mhpmcounter18h)
RO32(0xB93, mhpmcounter19h)
RO32(0xB94, mhpmcounter20h)
RO32(0xB95, mhpmcounter21h)
RO32(0xB96, mhpmcounter22h)
RO32(0xB97, mhpmcounter23h)
RO32(0xB98, mhpmcounter24h)
RO32(0xB99, mhpmcounter25h)
RO32(0xB9A, mhpmcounter26h)
RO32(0xB9B, mhpmcounter27h)
RO32(0xB9C, mhpmcounter28h)
RO32(0xB9D, mhpmcounter29h)
RO32(0xB9E, mhpmcounter30h)
RO32(0xB9F, mhpmcounter31h)
RW(0x323, mhpmevent3) // Machine performance-monitoring event selector
RW(0x324, mhpmevent4) // Machine performance-monitoring event selector
RW(0x325, mhpmevent5) // Machine performance-monitoring event selector
RW(0x326, mhpmevent6) // Machine performance-monitoring event selector
RW(0x327, mhpmevent7) // Machine performance-monitoring event selector
RW(0x328, mhpmevent8) // Machine performance-monitoring event selector
RW(0x329, mhpmevent9) // Machine performance-monitoring event selector
RW(0x32A, mhpmevent10) // Machine performance-monitoring event selector
RW(0x32B, mhpmevent11) // Machine performance-monitoring event selector
RW(0x32C, mhpmevent12) // Machine performance-monitoring event selector
RW(0x32D, mhpmevent13) // Machine performance-monitoring event selector
RW(0x32E, mhpmevent14) // Machine performance-monitoring event selector
RW(0x32F, mhpmevent15) // Machine performance-monitoring event selector
RW(0x330, mhpmevent16) // Machine performance-monitoring event selector
RW(0x331, mhpmevent17) // Machine performance-monitoring event selector
RW(0x332, mhpmevent18) // Machine performance-monitoring event selector
RW(0x333, mhpmevent19) // Machine performance-monitoring event selector
RW(0x334, mhpmevent20) // Machine performance-monitoring event selector
RW(0x335, mhpmevent21) // Machine performance-monitoring event selector
RW(0x336, mhpmevent22) // Machine performance-monitoring event selector
RW(0x337, mhpmevent23) // Machine performance-monitoring event selector
RW(0x338, mhpmevent24) // Machine performance-monitoring event selector
RW(0x339, mhpmevent25) // Machine performance-monitoring event selector
RW(0x33A, mhpmevent26) // Machine performance-monitoring event selector
RW(0x33B, mhpmevent27) // Machine performance-monitoring event selector
RW(0x33C, mhpmevent28) // Machine performance-monitoring event selector
RW(0x33D, mhpmevent29) // Machine performance-monitoring event selector
RW(0x33E, mhpmevent30) // Machine performance-monitoring event selector
RW(0x33F, mhpmevent31) // Machine performance-monitoring event selector
// Debug/Trace Registers (shared with Debug Mode)
RW(0x7A0, tselect) // Debug/Trace trigger register select
RW(0x7A1, tdata1) // First Debug/Trace trigger data register
RW(0x7A2, tdata2) // Second Debug/Trace trigger data register
RW(0x7A3, tdata3) // Third Debug/Trace trigger data register
// Debug Mode Registers
RW(0x7B0, dcsr) // Debug control and status register
RW(0x7B1, dpc) // Debug PC
RW(0x7B2, dscratch) // Debug scratch register

11
asm.h
View File

@ -33,5 +33,16 @@ __clear_ ## name: \
#define REG_READ_WRITE(name, offset) REG_READ(name, offset); REG_WRITE(name, offset)
#define REG_SET_CLEAR(name, offset) REG_SET(name, offset); REG_CLEAR(name, offset)
#define RW(offset, name) REG_READ_WRITE(name, offset); REG_SET_CLEAR(name, offset)
#define RO(offset, name) REG_READ(name, offset)
#if __riscv_xlen == 32
#define RW32(offset, name) RW(offset, name)
#define RO32(offset, name) RO(offset, name)
#else
#define RW32(offset, name)
#define RO32(offset, name)
#endif
#endif /* __ASM_H */

View File

@ -1,5 +0,0 @@
#include "asm.h"
REG_READ(mcycleh, 0xB80)
REG_READ(minstreth, 0xB82)
REG_READ(timeh, 0xC81)

View File

@ -7,14 +7,12 @@ crate=riscv
# remove existing blobs because otherwise this will append object files to the old blobs
rm -f bin/*.a
riscv64-unknown-elf-gcc -c -mabi=ilp32 -march=rv32imac asm.S -o bin/$crate.o
riscv64-unknown-elf-gcc -c -mabi=ilp32 -march=rv32imac asm32.S -o bin/$crate-32.o
ar crs bin/riscv32imac-unknown-none-elf.a bin/$crate.o bin/$crate-32.o
ar crs bin/riscv32imc-unknown-none-elf.a bin/$crate.o bin/$crate-32.o
riscv64-unknown-elf-gcc -c -mabi=ilp32 -march=rv32imc asm.S -o bin/$crate.o
ar crs bin/riscv32imac-unknown-none-elf.a bin/$crate.o
ar crs bin/riscv32imc-unknown-none-elf.a bin/$crate.o
riscv64-unknown-elf-gcc -c -mabi=lp64 -march=rv64imac asm.S -o bin/$crate.o
ar crs bin/riscv64imac-unknown-none-elf.a bin/$crate.o
ar crs bin/riscv64gc-unknown-none-elf.a bin/$crate.o
rm bin/$crate.o
rm bin/$crate-32.o

Binary file not shown.

Binary file not shown.

Binary file not shown.

Binary file not shown.

View File

@ -64,6 +64,7 @@ impl Flags {
}
/// Rounding Mode
#[derive(Clone, Copy, Debug, Eq, PartialEq)]
pub enum RoundingMode {
RoundToNearestEven = 0b000,
RoundTowardsZero = 0b001,

View File

@ -0,0 +1,82 @@
macro_rules! reg {
(
$addr:expr, $csrl:ident, $csrh:ident, $readf:ident, $writef:ident
) => {
/// Performance-monitoring counter
pub mod $csrl {
read_csr_as_usize!($addr, $readf);
read_composite_csr!(super::$csrh::read(), read());
}
}
}
macro_rules! regh {
(
$addr:expr, $csrh:ident, $readf:ident, $writef:ident
) => {
/// Upper 32 bits of performance-monitoring counter (RV32I only)
pub mod $csrh {
read_csr_as_usize_rv32!($addr, $readf);
}
}
}
reg!(0xC03, hpmcounter3, hpmcounter3h, __read_hpmcounter3, __write_hpmcounter3);
reg!(0xC04, hpmcounter4, hpmcounter4h, __read_hpmcounter4, __write_hpmcounter4);
reg!(0xC05, hpmcounter5, hpmcounter5h, __read_hpmcounter5, __write_hpmcounter5);
reg!(0xC06, hpmcounter6, hpmcounter6h, __read_hpmcounter6, __write_hpmcounter6);
reg!(0xC07, hpmcounter7, hpmcounter7h, __read_hpmcounter7, __write_hpmcounter7);
reg!(0xC08, hpmcounter8, hpmcounter8h, __read_hpmcounter8, __write_hpmcounter8);
reg!(0xC09, hpmcounter9, hpmcounter9h, __read_hpmcounter9, __write_hpmcounter9);
reg!(0xC0A, hpmcounter10, hpmcounter10h, __read_hpmcounter10, __write_hpmcounter10);
reg!(0xC0B, hpmcounter11, hpmcounter11h, __read_hpmcounter11, __write_hpmcounter11);
reg!(0xC0C, hpmcounter12, hpmcounter12h, __read_hpmcounter12, __write_hpmcounter12);
reg!(0xC0D, hpmcounter13, hpmcounter13h, __read_hpmcounter13, __write_hpmcounter13);
reg!(0xC0E, hpmcounter14, hpmcounter14h, __read_hpmcounter14, __write_hpmcounter14);
reg!(0xC0F, hpmcounter15, hpmcounter15h, __read_hpmcounter15, __write_hpmcounter15);
reg!(0xC10, hpmcounter16, hpmcounter16h, __read_hpmcounter16, __write_hpmcounter16);
reg!(0xC11, hpmcounter17, hpmcounter17h, __read_hpmcounter17, __write_hpmcounter17);
reg!(0xC12, hpmcounter18, hpmcounter18h, __read_hpmcounter18, __write_hpmcounter18);
reg!(0xC13, hpmcounter19, hpmcounter19h, __read_hpmcounter19, __write_hpmcounter19);
reg!(0xC14, hpmcounter20, hpmcounter20h, __read_hpmcounter20, __write_hpmcounter20);
reg!(0xC15, hpmcounter21, hpmcounter21h, __read_hpmcounter21, __write_hpmcounter21);
reg!(0xC16, hpmcounter22, hpmcounter22h, __read_hpmcounter22, __write_hpmcounter22);
reg!(0xC17, hpmcounter23, hpmcounter23h, __read_hpmcounter23, __write_hpmcounter23);
reg!(0xC18, hpmcounter24, hpmcounter24h, __read_hpmcounter24, __write_hpmcounter24);
reg!(0xC19, hpmcounter25, hpmcounter25h, __read_hpmcounter25, __write_hpmcounter25);
reg!(0xC1A, hpmcounter26, hpmcounter26h, __read_hpmcounter26, __write_hpmcounter26);
reg!(0xC1B, hpmcounter27, hpmcounter27h, __read_hpmcounter27, __write_hpmcounter27);
reg!(0xC1C, hpmcounter28, hpmcounter28h, __read_hpmcounter28, __write_hpmcounter28);
reg!(0xC1D, hpmcounter29, hpmcounter29h, __read_hpmcounter29, __write_hpmcounter29);
reg!(0xC1E, hpmcounter30, hpmcounter30h, __read_hpmcounter30, __write_hpmcounter30);
reg!(0xC1F, hpmcounter31, hpmcounter31h, __read_hpmcounter31, __write_hpmcounter31);
regh!(0xC83, hpmcounter3h, __read_hpmcounter3h, __write_hpmcounter3h);
regh!(0xC84, hpmcounter4h, __read_hpmcounter4h, __write_hpmcounter4h);
regh!(0xC85, hpmcounter5h, __read_hpmcounter5h, __write_hpmcounter5h);
regh!(0xC86, hpmcounter6h, __read_hpmcounter6h, __write_hpmcounter6h);
regh!(0xC87, hpmcounter7h, __read_hpmcounter7h, __write_hpmcounter7h);
regh!(0xC88, hpmcounter8h, __read_hpmcounter8h, __write_hpmcounter8h);
regh!(0xC89, hpmcounter9h, __read_hpmcounter9h, __write_hpmcounter9h);
regh!(0xC8A, hpmcounter10h, __read_hpmcounter10h, __write_hpmcounter10h);
regh!(0xC8B, hpmcounter11h, __read_hpmcounter11h, __write_hpmcounter11h);
regh!(0xC8C, hpmcounter12h, __read_hpmcounter12h, __write_hpmcounter12h);
regh!(0xC8D, hpmcounter13h, __read_hpmcounter13h, __write_hpmcounter13h);
regh!(0xC8E, hpmcounter14h, __read_hpmcounter14h, __write_hpmcounter14h);
regh!(0xC8F, hpmcounter15h, __read_hpmcounter15h, __write_hpmcounter15h);
regh!(0xC90, hpmcounter16h, __read_hpmcounter16h, __write_hpmcounter16h);
regh!(0xC91, hpmcounter17h, __read_hpmcounter17h, __write_hpmcounter17h);
regh!(0xC92, hpmcounter18h, __read_hpmcounter18h, __write_hpmcounter18h);
regh!(0xC93, hpmcounter19h, __read_hpmcounter19h, __write_hpmcounter19h);
regh!(0xC94, hpmcounter20h, __read_hpmcounter20h, __write_hpmcounter20h);
regh!(0xC95, hpmcounter21h, __read_hpmcounter21h, __write_hpmcounter21h);
regh!(0xC96, hpmcounter22h, __read_hpmcounter22h, __write_hpmcounter22h);
regh!(0xC97, hpmcounter23h, __read_hpmcounter23h, __write_hpmcounter23h);
regh!(0xC98, hpmcounter24h, __read_hpmcounter24h, __write_hpmcounter24h);
regh!(0xC99, hpmcounter25h, __read_hpmcounter25h, __write_hpmcounter25h);
regh!(0xC9A, hpmcounter26h, __read_hpmcounter26h, __write_hpmcounter26h);
regh!(0xC9B, hpmcounter27h, __read_hpmcounter27h, __write_hpmcounter27h);
regh!(0xC9C, hpmcounter28h, __read_hpmcounter28h, __write_hpmcounter28h);
regh!(0xC9D, hpmcounter29h, __read_hpmcounter29h, __write_hpmcounter29h);
regh!(0xC9E, hpmcounter30h, __read_hpmcounter30h, __write_hpmcounter30h);
regh!(0xC9F, hpmcounter31h, __read_hpmcounter31h, __write_hpmcounter31h);

View File

@ -118,6 +118,32 @@ macro_rules! write_csr {
};
}
macro_rules! write_csr_rv32 {
($csr_number:expr, $asm_fn: ident) => {
/// Writes the CSR
#[inline]
#[allow(unused_variables)]
unsafe fn _write(bits: usize) {
match () {
#[cfg(all(riscv32, feature = "inline-asm"))]
() => asm!("csrrw x0, $1, $0" :: "r"(bits), "i"($csr_number) :: "volatile"),
#[cfg(all(riscv32, not(feature = "inline-asm")))]
() => {
extern "C" {
fn $asm_fn(bits: usize);
}
$asm_fn(bits);
}
#[cfg(not(riscv32))]
() => unimplemented!(),
}
}
};
}
macro_rules! write_csr_as_usize {
($csr_number:expr, $asm_fn: ident) => {
write_csr!($csr_number, $asm_fn);
@ -130,6 +156,18 @@ macro_rules! write_csr_as_usize {
};
}
macro_rules! write_csr_as_usize_rv32 {
($csr_number:expr, $asm_fn: ident) => {
write_csr_rv32!($csr_number, $asm_fn);
/// Writes the CSR
#[inline]
pub fn write(bits: usize) {
unsafe{ _write(bits) }
}
};
}
macro_rules! set {
($csr_number:expr, $asm_fn: ident) => {
/// Set the CSR

View File

@ -7,14 +7,14 @@ pub struct Mcause {
}
/// Trap Cause
#[derive(Copy, Clone, Debug)]
#[derive(Copy, Clone, Debug, PartialEq, Eq)]
pub enum Trap {
Interrupt(Interrupt),
Exception(Exception),
}
/// Interrupt
#[derive(Copy, Clone, Debug)]
#[derive(Copy, Clone, Debug, PartialEq, Eq)]
pub enum Interrupt {
UserSoft,
SupervisorSoft,
@ -29,7 +29,7 @@ pub enum Interrupt {
}
/// Exception
#[derive(Copy, Clone, Debug)]
#[derive(Copy, Clone, Debug, PartialEq, Eq)]
pub enum Exception {
InstructionMisaligned,
InstructionFault,

View File

@ -1,3 +1,4 @@
//! mepc register
read_csr_as_usize!(0x341, __read_mepc);
write_csr_as_usize!(0x341, __write_mepc);

View File

@ -0,0 +1,84 @@
macro_rules! reg {
(
$addr:expr, $csrl:ident, $csrh:ident, $readf:ident, $writef:ident
) => {
/// Machine performance-monitoring counter
pub mod $csrl {
read_csr_as_usize!($addr, $readf);
write_csr_as_usize!($addr, $writef);
read_composite_csr!(super::$csrh::read(), read());
}
}
}
macro_rules! regh {
(
$addr:expr, $csrh:ident, $readf:ident, $writef:ident
) => {
/// Upper 32 bits of machine performance-monitoring counter (RV32I only)
pub mod $csrh {
read_csr_as_usize_rv32!($addr, $readf);
write_csr_as_usize_rv32!($addr, $writef);
}
}
}
reg!(0xB03, mhpmcounter3, mhpmcounter3h, __read_mhpmcounter3, __write_mhpmcounter3);
reg!(0xB04, mhpmcounter4, mhpmcounter4h, __read_mhpmcounter4, __write_mhpmcounter4);
reg!(0xB05, mhpmcounter5, mhpmcounter5h, __read_mhpmcounter5, __write_mhpmcounter5);
reg!(0xB06, mhpmcounter6, mhpmcounter6h, __read_mhpmcounter6, __write_mhpmcounter6);
reg!(0xB07, mhpmcounter7, mhpmcounter7h, __read_mhpmcounter7, __write_mhpmcounter7);
reg!(0xB08, mhpmcounter8, mhpmcounter8h, __read_mhpmcounter8, __write_mhpmcounter8);
reg!(0xB09, mhpmcounter9, mhpmcounter9h, __read_mhpmcounter9, __write_mhpmcounter9);
reg!(0xB0A, mhpmcounter10, mhpmcounter10h, __read_mhpmcounter10, __write_mhpmcounter10);
reg!(0xB0B, mhpmcounter11, mhpmcounter11h, __read_mhpmcounter11, __write_mhpmcounter11);
reg!(0xB0C, mhpmcounter12, mhpmcounter12h, __read_mhpmcounter12, __write_mhpmcounter12);
reg!(0xB0D, mhpmcounter13, mhpmcounter13h, __read_mhpmcounter13, __write_mhpmcounter13);
reg!(0xB0E, mhpmcounter14, mhpmcounter14h, __read_mhpmcounter14, __write_mhpmcounter14);
reg!(0xB0F, mhpmcounter15, mhpmcounter15h, __read_mhpmcounter15, __write_mhpmcounter15);
reg!(0xB10, mhpmcounter16, mhpmcounter16h, __read_mhpmcounter16, __write_mhpmcounter16);
reg!(0xB11, mhpmcounter17, mhpmcounter17h, __read_mhpmcounter17, __write_mhpmcounter17);
reg!(0xB12, mhpmcounter18, mhpmcounter18h, __read_mhpmcounter18, __write_mhpmcounter18);
reg!(0xB13, mhpmcounter19, mhpmcounter19h, __read_mhpmcounter19, __write_mhpmcounter19);
reg!(0xB14, mhpmcounter20, mhpmcounter20h, __read_mhpmcounter20, __write_mhpmcounter20);
reg!(0xB15, mhpmcounter21, mhpmcounter21h, __read_mhpmcounter21, __write_mhpmcounter21);
reg!(0xB16, mhpmcounter22, mhpmcounter22h, __read_mhpmcounter22, __write_mhpmcounter22);
reg!(0xB17, mhpmcounter23, mhpmcounter23h, __read_mhpmcounter23, __write_mhpmcounter23);
reg!(0xB18, mhpmcounter24, mhpmcounter24h, __read_mhpmcounter24, __write_mhpmcounter24);
reg!(0xB19, mhpmcounter25, mhpmcounter25h, __read_mhpmcounter25, __write_mhpmcounter25);
reg!(0xB1A, mhpmcounter26, mhpmcounter26h, __read_mhpmcounter26, __write_mhpmcounter26);
reg!(0xB1B, mhpmcounter27, mhpmcounter27h, __read_mhpmcounter27, __write_mhpmcounter27);
reg!(0xB1C, mhpmcounter28, mhpmcounter28h, __read_mhpmcounter28, __write_mhpmcounter28);
reg!(0xB1D, mhpmcounter29, mhpmcounter29h, __read_mhpmcounter29, __write_mhpmcounter29);
reg!(0xB1E, mhpmcounter30, mhpmcounter30h, __read_mhpmcounter30, __write_mhpmcounter30);
reg!(0xB1F, mhpmcounter31, mhpmcounter31h, __read_mhpmcounter31, __write_mhpmcounter31);
regh!(0xB83, mhpmcounter3h, __read_mhpmcounter3h, __write_mhpmcounter3h);
regh!(0xB84, mhpmcounter4h, __read_mhpmcounter4h, __write_mhpmcounter4h);
regh!(0xB85, mhpmcounter5h, __read_mhpmcounter5h, __write_mhpmcounter5h);
regh!(0xB86, mhpmcounter6h, __read_mhpmcounter6h, __write_mhpmcounter6h);
regh!(0xB87, mhpmcounter7h, __read_mhpmcounter7h, __write_mhpmcounter7h);
regh!(0xB88, mhpmcounter8h, __read_mhpmcounter8h, __write_mhpmcounter8h);
regh!(0xB89, mhpmcounter9h, __read_mhpmcounter9h, __write_mhpmcounter9h);
regh!(0xB8A, mhpmcounter10h, __read_mhpmcounter10h, __write_mhpmcounter10h);
regh!(0xB8B, mhpmcounter11h, __read_mhpmcounter11h, __write_mhpmcounter11h);
regh!(0xB8C, mhpmcounter12h, __read_mhpmcounter12h, __write_mhpmcounter12h);
regh!(0xB8D, mhpmcounter13h, __read_mhpmcounter13h, __write_mhpmcounter13h);
regh!(0xB8E, mhpmcounter14h, __read_mhpmcounter14h, __write_mhpmcounter14h);
regh!(0xB8F, mhpmcounter15h, __read_mhpmcounter15h, __write_mhpmcounter15h);
regh!(0xB90, mhpmcounter16h, __read_mhpmcounter16h, __write_mhpmcounter16h);
regh!(0xB91, mhpmcounter17h, __read_mhpmcounter17h, __write_mhpmcounter17h);
regh!(0xB92, mhpmcounter18h, __read_mhpmcounter18h, __write_mhpmcounter18h);
regh!(0xB93, mhpmcounter19h, __read_mhpmcounter19h, __write_mhpmcounter19h);
regh!(0xB94, mhpmcounter20h, __read_mhpmcounter20h, __write_mhpmcounter20h);
regh!(0xB95, mhpmcounter21h, __read_mhpmcounter21h, __write_mhpmcounter21h);
regh!(0xB96, mhpmcounter22h, __read_mhpmcounter22h, __write_mhpmcounter22h);
regh!(0xB97, mhpmcounter23h, __read_mhpmcounter23h, __write_mhpmcounter23h);
regh!(0xB98, mhpmcounter24h, __read_mhpmcounter24h, __write_mhpmcounter24h);
regh!(0xB99, mhpmcounter25h, __read_mhpmcounter25h, __write_mhpmcounter25h);
regh!(0xB9A, mhpmcounter26h, __read_mhpmcounter26h, __write_mhpmcounter26h);
regh!(0xB9B, mhpmcounter27h, __read_mhpmcounter27h, __write_mhpmcounter27h);
regh!(0xB9C, mhpmcounter28h, __read_mhpmcounter28h, __write_mhpmcounter28h);
regh!(0xB9D, mhpmcounter29h, __read_mhpmcounter29h, __write_mhpmcounter29h);
regh!(0xB9E, mhpmcounter30h, __read_mhpmcounter30h, __write_mhpmcounter30h);
regh!(0xB9F, mhpmcounter31h, __read_mhpmcounter31h, __write_mhpmcounter31h);

View File

@ -0,0 +1,41 @@
macro_rules! reg {
(
$addr:expr, $csr:ident, $readf:ident, $writef:ident
) => {
/// Machine performance-monitoring event selector
pub mod $csr {
read_csr_as_usize!($addr, $readf);
write_csr_as_usize!($addr, $writef);
}
}
}
reg!(0x323, mhpmevent3, __read_mhpmevent3, __write_mhpmevent3);
reg!(0x324, mhpmevent4, __read_mhpmevent4, __write_mhpmevent4);
reg!(0x325, mhpmevent5, __read_mhpmevent5, __write_mhpmevent5);
reg!(0x326, mhpmevent6, __read_mhpmevent6, __write_mhpmevent6);
reg!(0x327, mhpmevent7, __read_mhpmevent7, __write_mhpmevent7);
reg!(0x328, mhpmevent8, __read_mhpmevent8, __write_mhpmevent8);
reg!(0x329, mhpmevent9, __read_mhpmevent9, __write_mhpmevent9);
reg!(0x32A, mhpmevent10, __read_mhpmevent10, __write_mhpmevent10);
reg!(0x32B, mhpmevent11, __read_mhpmevent11, __write_mhpmevent11);
reg!(0x32C, mhpmevent12, __read_mhpmevent12, __write_mhpmevent12);
reg!(0x32D, mhpmevent13, __read_mhpmevent13, __write_mhpmevent13);
reg!(0x32E, mhpmevent14, __read_mhpmevent14, __write_mhpmevent14);
reg!(0x32F, mhpmevent15, __read_mhpmevent15, __write_mhpmevent15);
reg!(0x330, mhpmevent16, __read_mhpmevent16, __write_mhpmevent16);
reg!(0x331, mhpmevent17, __read_mhpmevent17, __write_mhpmevent17);
reg!(0x332, mhpmevent18, __read_mhpmevent18, __write_mhpmevent18);
reg!(0x333, mhpmevent19, __read_mhpmevent19, __write_mhpmevent19);
reg!(0x334, mhpmevent20, __read_mhpmevent20, __write_mhpmevent20);
reg!(0x335, mhpmevent21, __read_mhpmevent21, __write_mhpmevent21);
reg!(0x336, mhpmevent22, __read_mhpmevent22, __write_mhpmevent22);
reg!(0x337, mhpmevent23, __read_mhpmevent23, __write_mhpmevent23);
reg!(0x338, mhpmevent24, __read_mhpmevent24, __write_mhpmevent24);
reg!(0x339, mhpmevent25, __read_mhpmevent25, __write_mhpmevent25);
reg!(0x33A, mhpmevent26, __read_mhpmevent26, __write_mhpmevent26);
reg!(0x33B, mhpmevent27, __read_mhpmevent27, __write_mhpmevent27);
reg!(0x33C, mhpmevent28, __read_mhpmevent28, __write_mhpmevent28);
reg!(0x33D, mhpmevent29, __read_mhpmevent29, __write_mhpmevent29);
reg!(0x33E, mhpmevent30, __read_mhpmevent30, __write_mhpmevent30);
reg!(0x33F, mhpmevent31, __read_mhpmevent31, __write_mhpmevent31);

View File

@ -9,6 +9,7 @@ pub struct Misa {
}
/// Machine XLEN
#[derive(Copy, Clone, Debug, Eq, PartialEq)]
pub enum MXL {
XLEN32,
XLEN64,

View File

@ -13,33 +13,91 @@
#[macro_use]
mod macros;
// TODO: User Trap Setup
// TODO: User Trap Handling
// User Floating-Point CSRs
// TODO: frm, fflags
pub mod fcsr;
pub mod marchid;
pub mod mcause;
pub mod mcycle;
pub mod mcycleh;
pub mod mepc;
pub mod mhartid;
pub mod mie;
pub mod mimpid;
pub mod minstret;
pub mod minstreth;
pub mod mip;
pub mod misa;
pub mod mstatus;
pub mod mtvec;
pub mod mvendorid;
// User Counter/Timers
// TODO: cycle[h], instret[h]
pub mod time;
mod hpmcounterx;
pub use self::hpmcounterx::*;
pub mod timeh;
// Supervisor Trap Setup
// TODO: sedeleg, sideleg
pub mod sstatus;
pub mod stvec;
pub mod sie;
pub mod sip;
pub mod scause;
pub mod stval;
pub mod satp;
pub mod stvec;
// TODO: scounteren
// Supervisor Trap Handling
pub mod sscratch;
pub mod sepc;
pub mod scause;
pub mod stval;
pub mod sip;
pub mod time;
pub mod timeh;
// Supervisor Protection and Translation
pub mod satp;
// Machine Information Registers
pub mod mvendorid;
pub mod marchid;
pub mod mimpid;
pub mod mhartid;
// Machine Trap Setup
pub mod mstatus;
pub mod misa;
// TODO: medeleg, mideleg
pub mod mie;
pub mod mtvec;
// TODO: mcounteren
// Machine Trap Handling
pub mod mscratch;
pub mod mepc;
pub mod mcause;
pub mod mtval;
pub mod mip;
// Machine Protection and Translation
mod pmpcfgx;
pub use self::pmpcfgx::*;
mod pmpaddrx;
pub use self::pmpaddrx::*;
// Machine Counter/Timers
pub mod mcycle;
pub mod minstret;
mod mhpmcounterx;
pub use self::mhpmcounterx::*;
pub mod mcycleh;
pub mod minstreth;
// Machine Counter Setup
mod mhpmeventx;
pub use self::mhpmeventx::*;
// TODO: Debug/Trace Registers (shared with Debug Mode)
// TODO: Debug Mode Registers

4
src/register/mscratch.rs Normal file
View File

@ -0,0 +1,4 @@
//! mscratch register
read_csr_as_usize!(0x340, __read_mscratch);
write_csr_as_usize!(0x340, __write_mscratch);

View File

@ -10,6 +10,7 @@ pub struct Mstatus {
}
/// Additional extension state
#[derive(Copy, Clone, Debug, Eq, PartialEq)]
pub enum XS {
/// All off
AllOff = 0,
@ -25,6 +26,7 @@ pub enum XS {
}
/// Floating-point extension state
#[derive(Copy, Clone, Debug, Eq, PartialEq)]
pub enum FS {
Off = 0,
Initial = 1,
@ -33,6 +35,7 @@ pub enum FS {
}
/// Machine Previous Privilege Mode
#[derive(Copy, Clone, Debug, Eq, PartialEq)]
pub enum MPP {
Machine = 3,
Supervisor = 1,
@ -40,6 +43,7 @@ pub enum MPP {
}
/// Supervisor Previous Privilege Mode
#[derive(Copy, Clone, Debug, Eq, PartialEq)]
pub enum SPP {
Supervisor = 1,
User = 0,

3
src/register/mtval.rs Normal file
View File

@ -0,0 +1,3 @@
//! mtval register
read_csr_as_usize!(0x343, __read_mtval);

View File

@ -7,6 +7,7 @@ pub struct Mtvec {
}
/// Trap mode
#[derive(Copy, Clone, Debug, Eq, PartialEq)]
pub enum TrapMode {
Direct = 0,
Vectored = 1,

28
src/register/pmpaddrx.rs Normal file
View File

@ -0,0 +1,28 @@
macro_rules! reg {
(
$addr:expr, $csr:ident, $readf:ident, $writef:ident
) => {
/// Physical memory protection address register
pub mod $csr {
read_csr_as_usize!($addr, $readf);
write_csr_as_usize!($addr, $writef);
}
}
}
reg!(0x3B0, pmpaddr0, __read_pmpaddr0, __write_pmpaddr0);
reg!(0x3B1, pmpaddr1, __read_pmpaddr1, __write_pmpaddr1);
reg!(0x3B2, pmpaddr2, __read_pmpaddr2, __write_pmpaddr2);
reg!(0x3B3, pmpaddr3, __read_pmpaddr3, __write_pmpaddr3);
reg!(0x3B4, pmpaddr4, __read_pmpaddr4, __write_pmpaddr4);
reg!(0x3B5, pmpaddr5, __read_pmpaddr5, __write_pmpaddr5);
reg!(0x3B6, pmpaddr6, __read_pmpaddr6, __write_pmpaddr6);
reg!(0x3B7, pmpaddr7, __read_pmpaddr7, __write_pmpaddr7);
reg!(0x3B8, pmpaddr8, __read_pmpaddr8, __write_pmpaddr8);
reg!(0x3B9, pmpaddr9, __read_pmpaddr9, __write_pmpaddr9);
reg!(0x3BA, pmpaddr10, __read_pmpaddr10, __write_pmpaddr10);
reg!(0x3BB, pmpaddr11, __read_pmpaddr11, __write_pmpaddr11);
reg!(0x3BC, pmpaddr12, __read_pmpaddr12, __write_pmpaddr12);
reg!(0x3BD, pmpaddr13, __read_pmpaddr13, __write_pmpaddr13);
reg!(0x3BE, pmpaddr14, __read_pmpaddr14, __write_pmpaddr14);
reg!(0x3BF, pmpaddr15, __read_pmpaddr15, __write_pmpaddr15);

23
src/register/pmpcfgx.rs Normal file
View File

@ -0,0 +1,23 @@
/// Physical memory protection configuration
pub mod pmpcfg0 {
read_csr_as_usize!(0x3A0, __read_pmpcfg0);
write_csr_as_usize!(0x3A0, __write_pmpcfg0);
}
/// Physical memory protection configuration, RV32 only
pub mod pmpcfg1 {
read_csr_as_usize_rv32!(0x3A1, __read_pmpcfg1);
write_csr_as_usize_rv32!(0x3A1, __write_pmpcfg1);
}
/// Physical memory protection configuration
pub mod pmpcfg2 {
read_csr_as_usize!(0x3A2, __read_pmpcfg2);
write_csr_as_usize!(0x3A2, __write_pmpcfg2);
}
/// Physical memory protection configuration, RV32 only
pub mod pmpcfg3 {
read_csr_as_usize_rv32!(0x3A3, __read_pmpcfg3);
write_csr_as_usize_rv32!(0x3A3, __write_pmpcfg3);
}

View File

@ -70,12 +70,14 @@ impl Satp {
}
#[cfg(riscv32)]
#[derive(Clone, Copy, Debug, Eq, PartialEq)]
pub enum Mode {
Bare = 0,
Sv32 = 1,
}
#[cfg(riscv64)]
#[derive(Clone, Copy, Debug, Eq, PartialEq)]
pub enum Mode {
Bare = 0,
Sv39 = 8,

View File

@ -10,14 +10,14 @@ pub struct Scause {
}
/// Trap Cause
#[derive(Copy, Clone, Debug)]
#[derive(Copy, Clone, Debug, Eq, PartialEq)]
pub enum Trap {
Interrupt(Interrupt),
Exception(Exception),
}
/// Interrupt
#[derive(Copy, Clone, Debug)]
#[derive(Copy, Clone, Debug, Eq, PartialEq)]
pub enum Interrupt {
UserSoft,
SupervisorSoft,
@ -29,7 +29,7 @@ pub enum Interrupt {
}
/// Exception
#[derive(Copy, Clone, Debug)]
#[derive(Copy, Clone, Debug, Eq, PartialEq)]
pub enum Exception {
InstructionMisaligned,
InstructionFault,

View File

@ -10,14 +10,14 @@ pub struct Sstatus {
}
/// Supervisor Previous Privilege Mode
#[derive(Eq, PartialEq)]
#[derive(Copy, Clone, Debug, Eq, PartialEq)]
pub enum SPP {
Supervisor = 1,
User = 0,
}
/// Floating-point unit Status
#[derive(Eq, PartialEq)]
#[derive(Copy, Clone, Debug, Eq, PartialEq)]
pub enum FS {
Off = 0,
Initial = 1,

View File

@ -7,6 +7,7 @@ pub struct Stvec {
}
/// Trap mode
#[derive(Copy, Clone, Debug, Eq, PartialEq)]
pub enum TrapMode {
Direct = 0,
Vectored = 1,