1 /* 2 * Copyright (c) 2020 BayLibre, SAS 3 * 4 * SPDX-License-Identifier: Apache-2.0 5 */ 6 7 #ifndef CORE_PMP_H_ 8 #define CORE_PMP_H_ 9 10 /* Configuration register flags (cfg_val)*/ 11 #define PMP_R 0x01 /* Allow read */ 12 #define PMP_W 0x02 /* Allow write */ 13 #define PMP_X 0x04 /* Allow execute */ 14 #define PMP_A 0x18 /* Address-matching mode field */ 15 #define PMP_L 0x80 /* PMP entry is locked */ 16 #define PMP_OFF 0x00 /* Null region */ 17 #define PMP_TOR 0x08 /* Top of range */ 18 #define PMP_NA4 0x10 /* Naturally aligned four-byte region */ 19 #define PMP_NAPOT 0x18 /* Naturally aligned power-of-two region */ 20 21 #define PMP_SHIFT_ADDR 2 22 #define PMP_TYPE_MASK 0x18 23 #define TO_PMP_ADDR(addr) ((addr) >> PMP_SHIFT_ADDR) 24 #define FROM_PMP_ADDR(addr) ((addr) << PMP_SHIFT_ADDR) 25 #define TO_NAPOT_RANGE(size) (((size) - 1) >> 1) 26 #define TO_PMP_NAPOT(addr, size) TO_PMP_ADDR(addr | \ 27 TO_NAPOT_RANGE(size)) 28 29 #ifdef CONFIG_PMP_STACK_GUARD 30 31 #define PMP_GUARD_ALIGN_AND_SIZE CONFIG_PMP_STACK_GUARD_MIN_SIZE 32 33 #else 34 35 #define PMP_GUARD_ALIGN_AND_SIZE 0 36 37 #endif /* CONFIG_PMP_STACK_GUARD */ 38 39 #ifdef CONFIG_RISCV_PMP 40 41 /* 42 * @brief Set a Physical Memory Protection slot 43 * 44 * Configure a memory region to be secured by one of the 16 PMP entries. 45 * 46 * @param index Number of the targeted PMP entrie (0 to 15 only). 47 * @param cfg_val Configuration value (cf datasheet or defined flags) 48 * @param addr_val Address register value 49 * 50 * This function shall only be called from Secure state. 51 * 52 * @return -1 if bad argument, 0 otherwise. 53 */ 54 int z_riscv_pmp_set(unsigned int index, ulong_t cfg_val, ulong_t addr_val); 55 56 /* 57 * @brief Reset to 0 all PMP setup registers 58 */ 59 void z_riscv_pmp_clear_config(void); 60 61 /* 62 * @brief Print PMP setup register for info/debug 63 */ 64 void z_riscv_pmp_print(unsigned int index); 65 #endif /* CONFIG_RISCV_PMP */ 66 67 #if defined(CONFIG_USERSPACE) 68 69 /* 70 * @brief Configure RISCV user thread access to the stack 71 * 72 * Determine and save allow access setup in thread structure. 73 * 74 * @param thread Thread info data pointer. 75 */ 76 void z_riscv_init_user_accesses(struct k_thread *thread); 77 78 /* 79 * @brief Apply RISCV user thread access to the stack 80 * 81 * Write user access setup saved in this thread structure. 82 * 83 * @param thread Thread info data pointer. 84 */ 85 void z_riscv_configure_user_allowed_stack(struct k_thread *thread); 86 87 /* 88 * @brief Add a new RISCV stack access 89 * 90 * Add a new memory permission area in the existing 91 * pmp setup of the thread. 92 * 93 * @param thread Thread info data pointer. 94 * @param addr Start address of the memory area. 95 * @param size Size of the memory area. 96 * @param flags Pemissions: PMP_R, PMP_W, PMP_X, PMP_L 97 */ 98 void z_riscv_pmp_add_dynamic(struct k_thread *thread, 99 ulong_t addr, 100 ulong_t size, 101 unsigned char flags); 102 #endif /* CONFIG_USERSPACE */ 103 104 #ifdef CONFIG_PMP_STACK_GUARD 105 106 /* 107 * @brief Configure RISCV stack guard for interrupt stack 108 * 109 * Write PMP registers to prevent RWX access from all privilege mode. 110 */ 111 void z_riscv_configure_interrupt_stack_guard(void); 112 113 /* 114 * @brief Configure RISCV stack guard 115 * 116 * Determine and save stack guard setup in thread structure. 117 * 118 * @param thread Thread info data pointer. 119 */ 120 void z_riscv_init_stack_guard(struct k_thread *thread); 121 122 /* 123 * @brief Apply RISCV stack guard 124 * 125 * Write stack guard setup saved in this thread structure. 126 * 127 * @param thread Thread info data pointer. 128 */ 129 void z_riscv_configure_stack_guard(struct k_thread *thread); 130 #endif /* CONFIG_PMP_STACK_GUARD */ 131 132 #if defined(CONFIG_PMP_STACK_GUARD) || defined(CONFIG_USERSPACE) 133 134 /* 135 * @brief Initialize thread PMP setup value to 0 136 * 137 * @param thread Thread info data pointer. 138 */ 139 void z_riscv_pmp_init_thread(struct k_thread *thread); 140 #endif /* CONFIG_PMP_STACK_GUARD || CONFIG_USERSPACE */ 141 142 #endif /* CORE_PMP_H_ */ 143