1/* 2 * Copyright 2020, Data61, CSIRO (ABN 41 687 119 230) 3 * Copyright 2015, 2016 Hesham Almatary <heshamelmatary@gmail.com> 4 * 5 * SPDX-License-Identifier: GPL-2.0-only 6 */ 7 8#pragma once 9 10#include <util.h> 11 12#include <mode/hardware.h> 13 14/* Privileged CSR definitions */ 15#define SSTATUS_SPIE 0x00000020 16#define SSTATUS_SPP 0x00000100 17#define SSTATUS_FS 0x00006000 18 19#define SSTATUS_FS_CLEAN 0x00004000 20#define SSTATUS_FS_INITIAL 0x00002000 21#define SSTATUS_FS_DIRTY 0x00006000 22 23#define SATP_MODE_OFF 0 24#define SATP_MODE_SV32 1 25#define SATP_MODE_SV39 8 26#define SATP_MODE_SV48 9 27 28#ifndef __ASSEMBLER__ 29 30#include <config.h> 31#include <linker.h> 32 33#include <arch/types.h> 34#include <sel4/sel4_arch/constants.h> 35 36/* The size is for HiFive Unleashed */ 37#define L1_CACHE_LINE_SIZE_BITS 6 38#define L1_CACHE_LINE_SIZE BIT(L1_CACHE_LINE_SIZE_BITS) 39 40#define PAGE_BITS seL4_PageBits 41 42#define MODE_RESERVED 0 43 44/* MMU RISC-V related definitions. See RISC-V manual priv-1.10 */ 45 46/* Extract the n-level PT index from a virtual address. This works for any 47 * configured RISC-V system with CONFIG_PT_LEVEL (which can be 2 on Sv32, 48 * 3 on Sv38, or 4 on Sv48) 49 */ 50#define RISCV_GET_PT_INDEX(addr, n) (((addr) >> (((PT_INDEX_BITS) * (((CONFIG_PT_LEVELS) - 1) - (n))) + seL4_PageBits)) & MASK(PT_INDEX_BITS)) 51#define RISCV_GET_LVL_PGSIZE_BITS(n) (((PT_INDEX_BITS) * (((CONFIG_PT_LEVELS) - 1) - (n))) + seL4_PageBits) 52#define RISCV_GET_LVL_PGSIZE(n) BIT(RISCV_GET_LVL_PGSIZE_BITS((n))) 53/* 54 * These values are defined in RISC-V priv-1.10 manual, they represent the 55 * exception codes saved in scause register (by the hardware) on traps. 56 */ 57enum vm_fault_type { 58 RISCVInstructionMisaligned = 0, 59 RISCVInstructionAccessFault = 1, 60 RISCVInstructionIllegal = 2, 61 RISCVBreakpoint = 3, 62 /* reserved */ 63 RISCVLoadAccessFault = 5, 64 RISCVAddressMisaligned = 6, 65 RISCVStoreAccessFault = 7, 66 RISCVEnvCall = 8, 67 /* 9-11 reserved */ 68 RISCVInstructionPageFault = 12, 69 RISCVLoadPageFault = 13, 70 /* 14 - reserved */ 71 RISCVStorePageFault = 15 72 /* >= 16 reserved */ 73}; 74typedef word_t vm_fault_type_t; 75 76enum frameSizeConstants { 77 RISCVPageBits = seL4_PageBits, 78 RISCVMegaPageBits = seL4_LargePageBits, 79#if CONFIG_PT_LEVELS > 2 80 RISCVGigaPageBits = seL4_HugePageBits, 81#endif 82#if CONFIG_PT_LEVELS > 3 83 RISCVTeraPageBits = seL4_TeraPageBits 84#endif 85}; 86 87enum vm_page_size { 88 RISCV_4K_Page, 89 RISCV_Mega_Page, 90 RISCV_Giga_Page, 91 RISCV_Tera_Page 92}; 93typedef word_t vm_page_size_t; 94 95static inline word_t CONST pageBitsForSize(vm_page_size_t pagesize) 96{ 97 switch (pagesize) { 98 case RISCV_4K_Page: 99 return RISCVPageBits; 100 101 case RISCV_Mega_Page: 102 return RISCVMegaPageBits; 103 104#if CONFIG_PT_LEVELS > 2 105 case RISCV_Giga_Page: 106 return RISCVGigaPageBits; 107#endif 108 109#if CONFIG_PT_LEVELS > 3 110 case RISCV_Tera_Page: 111 return RISCVTeraPageBits; 112#endif 113 114 default: 115 fail("Invalid page size"); 116 } 117} 118 119static inline void arch_clean_invalidate_caches(void) 120{ 121 /* RISC-V doesn't have an architecture defined way of flushing caches */ 122} 123#endif /* __ASSEMBLER__ */ 124 125#define LOAD_S STRINGIFY(LOAD) 126#define STORE_S STRINGIFY(STORE) 127 128#define IPI_MEM_BARRIER \ 129 do { \ 130 asm volatile("fence rw,rw" ::: "memory"); \ 131 } while (0) 132 133