mirror of
https://github.com/plctlab/riscv-operating-system-mooc.git
synced 2025-12-26 09:09:11 +00:00
Encapsulate some types related to cpu word length.
The purpose is to facilitate porting to RV64. Signed-off-by: Wang Chen <wangchen20@iscas.ac.cn>
This commit is contained in:
@@ -1,3 +1,7 @@
|
||||
#define LOAD lw
|
||||
#define STORE sw
|
||||
#define SIZE_REG 4
|
||||
|
||||
# Save all General-Purpose(GP) registers to context.
|
||||
# struct context *base = &ctx_task;
|
||||
# base->ra = ra;
|
||||
@@ -10,34 +14,34 @@
|
||||
# which is a global value and would not be changed
|
||||
# during context-switch.
|
||||
.macro reg_save base
|
||||
sw ra, 0(\base)
|
||||
sw sp, 4(\base)
|
||||
sw t0, 16(\base)
|
||||
sw t1, 20(\base)
|
||||
sw t2, 24(\base)
|
||||
sw s0, 28(\base)
|
||||
sw s1, 32(\base)
|
||||
sw a0, 36(\base)
|
||||
sw a1, 40(\base)
|
||||
sw a2, 44(\base)
|
||||
sw a3, 48(\base)
|
||||
sw a4, 52(\base)
|
||||
sw a5, 56(\base)
|
||||
sw a6, 60(\base)
|
||||
sw a7, 64(\base)
|
||||
sw s2, 68(\base)
|
||||
sw s3, 72(\base)
|
||||
sw s4, 76(\base)
|
||||
sw s5, 80(\base)
|
||||
sw s6, 84(\base)
|
||||
sw s7, 88(\base)
|
||||
sw s8, 92(\base)
|
||||
sw s9, 96(\base)
|
||||
sw s10, 100(\base)
|
||||
sw s11, 104(\base)
|
||||
sw t3, 108(\base)
|
||||
sw t4, 112(\base)
|
||||
sw t5, 116(\base)
|
||||
STORE ra, 0*SIZE_REG(\base)
|
||||
STORE sp, 1*SIZE_REG(\base)
|
||||
STORE t0, 4*SIZE_REG(\base)
|
||||
STORE t1, 5*SIZE_REG(\base)
|
||||
STORE t2, 6*SIZE_REG(\base)
|
||||
STORE s0, 7*SIZE_REG(\base)
|
||||
STORE s1, 8*SIZE_REG(\base)
|
||||
STORE a0, 9*SIZE_REG(\base)
|
||||
STORE a1, 10*SIZE_REG(\base)
|
||||
STORE a2, 11*SIZE_REG(\base)
|
||||
STORE a3, 12*SIZE_REG(\base)
|
||||
STORE a4, 13*SIZE_REG(\base)
|
||||
STORE a5, 14*SIZE_REG(\base)
|
||||
STORE a6, 15*SIZE_REG(\base)
|
||||
STORE a7, 16*SIZE_REG(\base)
|
||||
STORE s2, 17*SIZE_REG(\base)
|
||||
STORE s3, 18*SIZE_REG(\base)
|
||||
STORE s4, 19*SIZE_REG(\base)
|
||||
STORE s5, 20*SIZE_REG(\base)
|
||||
STORE s6, 21*SIZE_REG(\base)
|
||||
STORE s7, 22*SIZE_REG(\base)
|
||||
STORE s8, 23*SIZE_REG(\base)
|
||||
STORE s9, 24*SIZE_REG(\base)
|
||||
STORE s10, 25*SIZE_REG(\base)
|
||||
STORE s11, 26*SIZE_REG(\base)
|
||||
STORE t3, 27*SIZE_REG(\base)
|
||||
STORE t4, 28*SIZE_REG(\base)
|
||||
STORE t5, 29*SIZE_REG(\base)
|
||||
# we don't save t6 here, due to we have used
|
||||
# it as base, we have to save t6 in an extra step
|
||||
# outside of reg_save
|
||||
@@ -49,35 +53,35 @@
|
||||
# ra = base->ra;
|
||||
# ......
|
||||
.macro reg_restore base
|
||||
lw ra, 0(\base)
|
||||
lw sp, 4(\base)
|
||||
lw t0, 16(\base)
|
||||
lw t1, 20(\base)
|
||||
lw t2, 24(\base)
|
||||
lw s0, 28(\base)
|
||||
lw s1, 32(\base)
|
||||
lw a0, 36(\base)
|
||||
lw a1, 40(\base)
|
||||
lw a2, 44(\base)
|
||||
lw a3, 48(\base)
|
||||
lw a4, 52(\base)
|
||||
lw a5, 56(\base)
|
||||
lw a6, 60(\base)
|
||||
lw a7, 64(\base)
|
||||
lw s2, 68(\base)
|
||||
lw s3, 72(\base)
|
||||
lw s4, 76(\base)
|
||||
lw s5, 80(\base)
|
||||
lw s6, 84(\base)
|
||||
lw s7, 88(\base)
|
||||
lw s8, 92(\base)
|
||||
lw s9, 96(\base)
|
||||
lw s10, 100(\base)
|
||||
lw s11, 104(\base)
|
||||
lw t3, 108(\base)
|
||||
lw t4, 112(\base)
|
||||
lw t5, 116(\base)
|
||||
lw t6, 120(\base)
|
||||
LOAD ra, 0*SIZE_REG(\base)
|
||||
LOAD sp, 1*SIZE_REG(\base)
|
||||
LOAD t0, 4*SIZE_REG(\base)
|
||||
LOAD t1, 5*SIZE_REG(\base)
|
||||
LOAD t2, 6*SIZE_REG(\base)
|
||||
LOAD s0, 7*SIZE_REG(\base)
|
||||
LOAD s1, 8*SIZE_REG(\base)
|
||||
LOAD a0, 9*SIZE_REG(\base)
|
||||
LOAD a1, 10*SIZE_REG(\base)
|
||||
LOAD a2, 11*SIZE_REG(\base)
|
||||
LOAD a3, 12*SIZE_REG(\base)
|
||||
LOAD a4, 13*SIZE_REG(\base)
|
||||
LOAD a5, 14*SIZE_REG(\base)
|
||||
LOAD a6, 15*SIZE_REG(\base)
|
||||
LOAD a7, 16*SIZE_REG(\base)
|
||||
LOAD s2, 17*SIZE_REG(\base)
|
||||
LOAD s3, 18*SIZE_REG(\base)
|
||||
LOAD s4, 19*SIZE_REG(\base)
|
||||
LOAD s5, 20*SIZE_REG(\base)
|
||||
LOAD s6, 21*SIZE_REG(\base)
|
||||
LOAD s7, 22*SIZE_REG(\base)
|
||||
LOAD s8, 23*SIZE_REG(\base)
|
||||
LOAD s9, 24*SIZE_REG(\base)
|
||||
LOAD s10, 25*SIZE_REG(\base)
|
||||
LOAD s11, 26*SIZE_REG(\base)
|
||||
LOAD t3, 27*SIZE_REG(\base)
|
||||
LOAD t4, 28*SIZE_REG(\base)
|
||||
LOAD t5, 29*SIZE_REG(\base)
|
||||
LOAD t6, 30*SIZE_REG(\base)
|
||||
.endm
|
||||
|
||||
# Something to note about save/restore:
|
||||
@@ -104,9 +108,9 @@ switch_to:
|
||||
|
||||
# Save the actual t6 register, which we swapped into
|
||||
# mscratch
|
||||
mv t5, t6 # t5 points to the context of current task
|
||||
csrr t6, mscratch # read t6 back from mscratch
|
||||
sw t6, 120(t5) # save t6 with t5 as base
|
||||
mv t5, t6 # t5 points to the context of current task
|
||||
csrr t6, mscratch # read t6 back from mscratch
|
||||
STORE t6, 30*SIZE_REG(t5) # save t6 with t5 as base
|
||||
|
||||
1:
|
||||
# switch mscratch to point to the context of the next task
|
||||
|
||||
@@ -1,30 +1,32 @@
|
||||
#define SIZE_PTR .word
|
||||
|
||||
.section .rodata
|
||||
.global HEAP_START
|
||||
HEAP_START: .word _heap_start
|
||||
HEAP_START: SIZE_PTR _heap_start
|
||||
|
||||
.global HEAP_SIZE
|
||||
HEAP_SIZE: .word _heap_size
|
||||
HEAP_SIZE: SIZE_PTR _heap_size
|
||||
|
||||
.global TEXT_START
|
||||
TEXT_START: .word _text_start
|
||||
TEXT_START: SIZE_PTR _text_start
|
||||
|
||||
.global TEXT_END
|
||||
TEXT_END: .word _text_end
|
||||
TEXT_END: SIZE_PTR _text_end
|
||||
|
||||
.global DATA_START
|
||||
DATA_START: .word _data_start
|
||||
DATA_START: SIZE_PTR _data_start
|
||||
|
||||
.global DATA_END
|
||||
DATA_END: .word _data_end
|
||||
DATA_END: SIZE_PTR _data_end
|
||||
|
||||
.global RODATA_START
|
||||
RODATA_START: .word _rodata_start
|
||||
RODATA_START: SIZE_PTR _rodata_start
|
||||
|
||||
.global RODATA_END
|
||||
RODATA_END: .word _rodata_end
|
||||
RODATA_END: SIZE_PTR _rodata_end
|
||||
|
||||
.global BSS_START
|
||||
BSS_START: .word _bss_start
|
||||
BSS_START: SIZE_PTR _bss_start
|
||||
|
||||
.global BSS_END
|
||||
BSS_END: .word _bss_end
|
||||
BSS_END: SIZE_PTR _bss_end
|
||||
|
||||
@@ -3,24 +3,24 @@
|
||||
/*
|
||||
* Following global vars are defined in mem.S
|
||||
*/
|
||||
extern uint32_t TEXT_START;
|
||||
extern uint32_t TEXT_END;
|
||||
extern uint32_t DATA_START;
|
||||
extern uint32_t DATA_END;
|
||||
extern uint32_t RODATA_START;
|
||||
extern uint32_t RODATA_END;
|
||||
extern uint32_t BSS_START;
|
||||
extern uint32_t BSS_END;
|
||||
extern uint32_t HEAP_START;
|
||||
extern uint32_t HEAP_SIZE;
|
||||
extern ptr_t TEXT_START;
|
||||
extern ptr_t TEXT_END;
|
||||
extern ptr_t DATA_START;
|
||||
extern ptr_t DATA_END;
|
||||
extern ptr_t RODATA_START;
|
||||
extern ptr_t RODATA_END;
|
||||
extern ptr_t BSS_START;
|
||||
extern ptr_t BSS_END;
|
||||
extern ptr_t HEAP_START;
|
||||
extern ptr_t HEAP_SIZE;
|
||||
|
||||
/*
|
||||
* _alloc_start points to the actual start address of heap pool
|
||||
* _alloc_end points to the actual end address of heap pool
|
||||
* _num_pages holds the actual max number of pages we can allocate.
|
||||
*/
|
||||
static uint32_t _alloc_start = 0;
|
||||
static uint32_t _alloc_end = 0;
|
||||
static ptr_t _alloc_start = 0;
|
||||
static ptr_t _alloc_end = 0;
|
||||
static uint32_t _num_pages = 0;
|
||||
|
||||
#define PAGE_SIZE 4096
|
||||
@@ -70,9 +70,9 @@ static inline int _is_last(struct Page *page)
|
||||
/*
|
||||
* align the address to the border of page(4K)
|
||||
*/
|
||||
static inline uint32_t _align_page(uint32_t address)
|
||||
static inline ptr_t _align_page(ptr_t address)
|
||||
{
|
||||
uint32_t order = (1 << PAGE_ORDER) - 1;
|
||||
ptr_t order = (1 << PAGE_ORDER) - 1;
|
||||
return (address + order) & (~order);
|
||||
}
|
||||
|
||||
@@ -155,12 +155,12 @@ void page_free(void *p)
|
||||
/*
|
||||
* Assert (TBD) if p is invalid
|
||||
*/
|
||||
if (!p || (uint32_t)p >= _alloc_end) {
|
||||
if (!p || (ptr_t)p >= _alloc_end) {
|
||||
return;
|
||||
}
|
||||
/* get the first page descriptor of this memory block */
|
||||
struct Page *page = (struct Page *)HEAP_START;
|
||||
page += ((uint32_t)p - _alloc_start)/ PAGE_SIZE;
|
||||
page += ((ptr_t)p - _alloc_start)/ PAGE_SIZE;
|
||||
/* loop and clear all the page descriptors of the memory block */
|
||||
while (!_is_free(page)) {
|
||||
if (_is_last(page)) {
|
||||
|
||||
@@ -5,7 +5,7 @@
|
||||
* QEMU RISC-V Virt machine with 16550a UART and VirtIO MMIO
|
||||
*/
|
||||
|
||||
/*
|
||||
/*
|
||||
* maximum number of CPUs
|
||||
* see https://github.com/qemu/qemu/blob/master/include/hw/riscv/virt.h
|
||||
* #define VIRT_CPUS_MAX 8
|
||||
@@ -14,7 +14,7 @@
|
||||
|
||||
/*
|
||||
* MemoryMap
|
||||
* see https://github.com/qemu/qemu/blob/master/hw/riscv/virt.c, virt_memmap[]
|
||||
* see https://github.com/qemu/qemu/blob/master/hw/riscv/virt.c, virt_memmap[]
|
||||
* 0x00001000 -- boot ROM, provided by qemu
|
||||
* 0x02000000 -- CLINT
|
||||
* 0x0C000000 -- PLIC
|
||||
|
||||
@@ -7,8 +7,9 @@ typedef unsigned int uint32_t;
|
||||
typedef unsigned long long uint64_t;
|
||||
|
||||
/*
|
||||
* RISCV32: register is 32bits width
|
||||
*/
|
||||
* Register Width
|
||||
*/
|
||||
typedef uint32_t reg_t;
|
||||
typedef uint32_t ptr_t;
|
||||
|
||||
#endif /* __TYPES_H__ */
|
||||
|
||||
Reference in New Issue
Block a user