1 /* 2 * Copyright (c) 2020 HiSilicon (Shanghai) Technologies CO., LIMITED. 3 * Licensed under the Apache License, Version 2.0 (the "License"); 4 * you may not use this file except in compliance with the License. 5 * You may obtain a copy of the License at 6 * 7 * http://www.apache.org/licenses/LICENSE-2.0 8 * 9 * Unless required by applicable law or agreed to in writing, software 10 * distributed under the License is distributed on an "AS IS" BASIS, 11 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 12 * See the License for the specific language governing permissions and 13 * limitations under the License. 14 */ 15 16 /** @defgroup mmu Memory management unit 17 * @ingroup mmu 18 */ 19 20 #ifndef __MMU_CONFIG_H 21 #define __MMU_CONFIG_H 22 23 #include "board.h" 24 #include "los_config.h" 25 #include "los_memory.h" 26 #include "mmu.h" 27 28 #ifdef __cplusplus 29 #if __cplusplus 30 extern "C" { 31 #endif /* __cplusplus */ 32 #endif /* __cplusplus */ 33 34 #define MMU_SET_PAGE_TABLE_PLACE \ 35 __attribute__((aligned(MMU_16K))) __attribute__((section(".bss.prebss.translation_table"))) UINT8 first_page_table[MMU_16K]; \ 36 __attribute__((aligned(MMU_1K))) UINT8 second_page_table_os[MMU_16K]; \ 37 __attribute__((aligned(MMU_1K))) UINT8 second_page_table_app[MMZ_MEM_LEN / MMU_1K]; 38 39 /** 40 * @ingroup mmu 41 * The liteos cache addr & length 42 */ 43 #define LITEOS_CACHE_ADDR SYS_MEM_BASE 44 #define LITEOS_CACHE_LENGTH (OS_SYS_FUNC_ADDR_END - LITEOS_CACHE_ADDR) 45 46 /** 47 * @ingroup mmu 48 * The page table storage addr 49 * notice: must ensure it has enough free mem for storage page table 50 */ 51 extern UINT8 first_page_table[MMU_16K]; 52 #define FIRST_PAGE_DESCRIPTOR_ADDR ((UINTPTR)first_page_table) 53 #define stAppPage g_mmuAppPage 54 55 #define X_MMU_SECOND_TABLE_OS_PAGE_SET() do { \ 56 g_mmuOsPage.page_addr = SYS_MEM_BASE; \ 57 g_mmuOsPage.page_length = ((((UINTPTR)&__ram_data_start - SYS_MEM_BASE) + MMU_1M - 1)& ~ (MMU_1M - 1)); \ 58 g_mmuOsPage.page_descriptor_addr = (UINTPTR)second_page_table_os; \ 59 g_mmuOsPage.page_type = MMU_SECOND_LEVEL_SMALL_PAGE_TABLE_ID; \ 60 if (g_mmuOsPage.page_length > (sizeof(second_page_table_os) << 10)) { \ 61 PRINT_ERR("%s,%d\n", __FUNCTION__, __LINE__); \ 62 PRINT_ERR("the mapping size of os second page is 0x%x, sholud be not bigger than 0x%x\n", \ 63 g_mmuOsPage.page_length, (sizeof(second_page_table_os) << 10)); \ 64 return; \ 65 } \ 66 LOS_SecPageEnable(&g_mmuOsPage, BUFFER_ENABLE | CACHE_ENABLE | ACCESS_PERM_RW_RW); \ 67 } while (0) 68 69 #define X_MMU_SECOND_TABLE_APP_PAGE_SET() \ 70 do { \ 71 stAppPage.page_addr = MMZ_MEM_BASE; \ 72 stAppPage.page_length = MMZ_MEM_LEN; \ 73 stAppPage.page_descriptor_addr = (UINTPTR)second_page_table_app; \ 74 stAppPage.page_type = MMU_SECOND_LEVEL_SMALL_PAGE_TABLE_ID; \ 75 LOS_SecPageEnable(&stAppPage, BUFFER_DISABLE | CACHE_DISABLE | ACCESS_PERM_RW_RW); \ 76 } while (0) 77 78 #define MMU_GET_FIRST_TABLE_ADDR(addr) (((addr) / MMU_1M)*4 + FIRST_PAGE_DESCRIPTOR_ADDR) // table start position + offset = 'addr' table item position 79 #define MMU_GET_FIRST_TABLE_ITEM(addr) (*(UINT32 *)MMU_GET_FIRST_TABLE_ADDR(addr)) // get item content which storaged by table 80 #define MMU_GET_SECOND_TABLE_BASE(addr) ((MMU_GET_FIRST_TABLE_ITEM(addr)) & 0xfffffc00) // if the first item ID is MMU_FIRST_LEVEL_PAGE_TABLE_ID, get second table item addr by hi 22bits 81 #define MMU_GET_SECOND_TABLE_OFFSET(addr) (((addr) % MMU_1M) / MMU_4K * 4) // second table item offset 82 #define MMU_GET_SECOND_TABLE_ADDR(addr) (MMU_GET_SECOND_TABLE_BASE(addr) + MMU_GET_SECOND_TABLE_OFFSET(addr)) 83 84 #define CODE_PROTECT do { \ 85 MMU_PARAM mPara; \ 86 /* note: must confirm that every addr be aglined as 4K(64K) */ \ 87 mPara.startAddr = (UINTPTR)&__text_start; \ 88 mPara.endAddr = (UINTPTR)&__ram_data_start; \ 89 mPara.uwFlag = BUFFER_ENABLE | CACHE_ENABLE | ACCESS_PERM_RO_RO; \ 90 mPara.stPage = (SENCOND_PAGE *)&g_mmuOsPage; \ 91 LOS_MMUParamSet(&mPara); \ 92 } while (0) 93 94 /** 95 * @ingroup mmu_config 96 * @brief Memory Management Unit Cache/Buffer/Access Permission Setting. 97 * 98 * @par Description: 99 * This API is used to set the Cache/Buffer/access permission mode of a section that is specified by a starting address and ending address 100 * @attention 101 * <ul> 102 * <li>The passed-in starting address and ending address must be aligned on a boundary of 4K. The access permission mode can be only set to ACCESS_PERM_RO_RO and ACCESS_PERM_RW_RW.</li> 103 * </ul> 104 * 105 * @param MMU_PARAM [IN] param for mmu setting, the struct contains below members 106 * startAddr: Starting address of a section. 107 * endAddr: Ending address of a section. 108 * uwFlag: mode set. There are three func could be controlled with three bit. 109 * bit0: ACCESS_PERM_RW_RW/ACCESS_PERM_RO_RO(1/0) 110 * bit1: CACHE_ENABLE/CACHE_DISABLE(1/0) 111 * bit2: BUFFER_ENABLE/BUFFER_DISABLE(1/0) 112 * bit3: FIRST_SECTION/SECOND_PAGE(1/0) it need comfire your memory type, be descripted 113 * bit4~7: ignore 114 * stPage: the goal object of second page, if uwFlag bit3 is FIRST_SECTION, stPage will be ignored, and you can set this member as NULL 115 * 116 * @retval None. 117 * @par Dependency: 118 * <ul><li>mmu.h: the header file that contains the API declaration.</li></ul> 119 * @see 120 */ 121 VOID LOS_MMUParamSet(MMU_PARAM *mPara); 122 #ifdef __cplusplus 123 #if __cplusplus 124 } 125 #endif /* __cplusplus */ 126 #endif /* __cplusplus */ 127 #endif 128