Add assembly constants file

This commit is contained in:
2025-08-02 00:12:28 +02:00
parent 3e50e74526
commit badac1378d
3 changed files with 133 additions and 67 deletions

View File

@@ -2,6 +2,8 @@
# v. 2.0. If a copy of the MPL was not distributed with this file, You can # v. 2.0. If a copy of the MPL was not distributed with this file, You can
# obtain one at https://mozilla.org/MPL/2.0/. # obtain one at https://mozilla.org/MPL/2.0/.
.include "./arch/riscv/constants.s"
.section .text .section .text
# a0 - First pointer. # a0 - First pointer.
@@ -237,3 +239,70 @@ memset:
.Lmemset_end: .Lmemset_end:
ret ret
# Maps a page of physical memory to the identical virtual memory.
#
# Parameters:
# a0 - Corresponding virtual address.
# a1 - Physical page address.
# a2 - Free memory page that can be used to create a leaf page table.
# a3 - Page table level. If a3 is 0 a superpage is allocated, otherwise a normal page.
# a4 - Flags.
#
# If the function creates new page tables in a2, it advances a2 by the page size and
# returns it in a0.
.type pmem_map_at, @function
.globl pmem_map_at
pmem_map_at:
csrr t0, satp
slli t0, t0, 12 # Root table address.
li t4, 0xfffffc00
li t5, 0xffc # 10 bit * PTESIZE mask.
li t1, 20
.Lpmem_map_at_loop:
# Multiply VPN[i] by 4 and add to the start address of the page table.
# This gives the physical address of the page table entry.
srl t2, a0, t1
and t2, t2, t5 # VPN[i] * PTESIZE.
add t2, t0, t2 # a + VPN[i] * PTESIZE.
beqz a3, .Lpmem_map_at_leaf
lw t3, (t2)
andi t6, t3, 0b1
beqz t6, .Lpmem_map_at_create
and t0, t3, t4
slli t0, t0, 2
j .Lpmem_map_at_next
.Lpmem_map_at_create:
# Take a chunk of free memory and use it as the next page table.
# The beginning addres off the chunk is the base address (a) for the next level.
mv t0, a2
srli t3, t0, 2
ori t3, t3, 0b1
sw t3, (t2)
li t6, PAGE_SIZE
add a2, a2, t6
.Lpmem_map_at_next:
# Calculate the next page table address for the next level.
addi t1, t1, -10
addi a3, a3, -1
j .Lpmem_map_at_loop
.Lpmem_map_at_leaf:
srli t3, a1, 2 # Physical page number mapped to 12 bits of the page table entry.
ori a4, a4, 0b1
or t3, t3, a4 # Execute, write, read and valid.
sw t3, (t2)
mv a0, a2
ret

1
arch/riscv/constants.s Normal file
View File

@@ -0,0 +1 @@
.equ PAGE_SIZE, 4096

View File

@@ -2,6 +2,8 @@
# v. 2.0. If a copy of the MPL was not distributed with this file, You can # v. 2.0. If a copy of the MPL was not distributed with this file, You can
# obtain one at https://mozilla.org/MPL/2.0/. # obtain one at https://mozilla.org/MPL/2.0/.
.include "./arch/riscv/constants.s"
.section .rodata .section .rodata
panic_message: .asciz "\nPanic" panic_message: .asciz "\nPanic"
@@ -104,12 +106,10 @@ set_up_stack:
# a1 - Memory end pointer. # a1 - Memory end pointer.
.type imem_zero, @function .type imem_zero, @function
imem_zero: imem_zero:
mv t0, a0
.Limem_zero_loop: .Limem_zero_loop:
bgeu t0, a1, .Limem_zero_end bgeu a0, a1, .Limem_zero_end
sw zero, (t0) sw zero, (a0)
addi t0, t0, 4 addi a0, a0, 4
j .Limem_zero_loop j .Limem_zero_loop
@@ -125,7 +125,7 @@ imem_mirror:
csrr t0, satp csrr t0, satp
slli t0, t0, 12 slli t0, t0, 12
li t3, 0x1000 li t3, PAGE_SIZE
add t1, t0, t3 # Original page table. add t1, t0, t3 # Original page table.
add t2, t1, t3 # Copied page table. add t2, t1, t3 # Copied page table.
@@ -167,9 +167,10 @@ imem_initialize:
sw s1, 16(sp) sw s1, 16(sp)
sw s2, 12(sp) sw s2, 12(sp)
sw s3, 8(sp) sw s3, 8(sp)
sw a0, 4(sp)
# Set s1 to the beginning of free memory (skipping root page table). # Set s1 to the beginning of free memory (skipping root page table).
li s1, 4096 li s1, PAGE_SIZE
add s1, a1, s1 add s1, a1, s1
slli a3, a3, 1 # Multiply by two to account for the copy in virtual memory. slli a3, a3, 1 # Multiply by two to account for the copy in virtual memory.
@@ -190,28 +191,28 @@ imem_initialize:
srli t0, a1, 12 srli t0, a1, 12
csrw satp, t0 csrw satp, t0
# Zero memory for page tables.
mv a0, a1
add a1, s1, a3
call imem_zero
# Executable section. # Executable section.
# a0 is coming from the parameter. mv a0, s1
addi a1, s2, %lo(etext) lw a1, 4(sp)
mv a2, s1 addi a2, s2, %lo(etext)
li a3, 1 li a3, 0b1010 # Read and execute.
li a4, 0b1010
jal imem_map_range jal imem_map_range
# Read only section. # Read only section.
addi a0, s2, %lo(etext) addi a1, s2, %lo(etext)
addi a1, s3, %lo(_data) addi a2, s3, %lo(_data)
mv a2, s1 li a3, 0b0010 # Read.
li a3, 1
li a4, 0b0010
jal imem_map_range jal imem_map_range
# Data section. # Data section.
addi a0, s3, %lo(_data) addi a1, s3, %lo(_data)
lw a1, 20(sp) lw a2, 20(sp)
mv a2, s1 li a3, 0b0110 # Read and write.
li a3, 1
li a4, 0b0110
jal imem_map_range jal imem_map_range
# Enable paging. # Enable paging.
@@ -236,11 +237,12 @@ imem_initialize:
# Maps multiple pages of physical memory to the identical virtual memory. # Maps multiple pages of physical memory to the identical virtual memory.
# #
# Parameters: # Parameters:
# a0 - Start address. # a0 - Start of the free memory that can be used to create leaf page tables.
# a1 - End address. # a1 - Start address.
# a2 - Start of the free memory that can be used to create leaf page tables. # a2 - End address.
# a3 - Page table level. If a3 is 0 a superpage is allocated, otherwise a normal page. # a3 - Flags.
# a4 - Flags. #
# If the function creates new page tables it advances and returns a0.
.type imem_map_range, @function .type imem_map_range, @function
imem_map_range: imem_map_range:
# Prologue. # Prologue.
@@ -250,27 +252,30 @@ imem_map_range:
addi s0, sp, 32 addi s0, sp, 32
sw s1, 20(sp) sw s1, 20(sp)
sw a2, 16(sp) sw s2, 16(sp)
sw a3, 12(sp) sw s3, 12(sp)
sw a4, 8(sp) sw s4, 8(sp)
mv s1, a1 mv s1, a1
mv s2, a2
li s3, PAGE_SIZE
mv s4, a3
.Limem_map_range_loop: .Limem_map_range_loop:
bge a0, s1, .Limem_map_range_end bge s1, s2, .Limem_map_range_end
mv a1, a0 mv a1, s1
lw a2, 16(sp) mv a2, s4
lw a3, 12(sp)
lw a4, 8(sp)
jal imem_map_at jal imem_map_at
li t0, 4096 add s1, s1, s3
add a0, a0, t0
j .Limem_map_range_loop j .Limem_map_range_loop
.Limem_map_range_end: .Limem_map_range_end:
lw s4, 8(sp)
lw s3, 12(sp)
lw s2, 16(sp)
lw s1, 20(sp) lw s1, 20(sp)
# Epilogue. # Epilogue.
@@ -282,62 +287,53 @@ imem_map_range:
# Maps a page of physical memory to the identical virtual memory. # Maps a page of physical memory to the identical virtual memory.
# #
# Parameters: # Parameters:
# a0 - Corresponding virtual address. # a0 - Free memory page that can be used to create a leaf page table.
# a1 - Physical page address. # a1 - Physical page address.
# a2 - Free memory page that can be used to create a leaf page table. # a2 - Flags.
# a3 - Page table level. If a3 is 0 a superpage is allocated, otherwise a normal page.
# a4 - Flags.
# #
# Returns virtual page address in a0. # If the function creates new page tables it advances and returns a0.
.type imem_map_at, @function .type imem_map_at, @function
imem_map_at: imem_map_at:
csrr t0, satp csrr t0, satp
slli t0, t0, 12 # Root table address. slli t0, t0, 12 # Root table address.
li t4, 0xfffffc00 li t1, 0xffc # 10 bit * PTESIZE mask.
li t5, 0xffc # 10 bit * PTESIZE mask.
li t1, 20
.Limem_map_at_loop: srli t2, a1, 20
# Multiply VPN[i] by 4 and add to the start address of the page table. and t2, t2, t1 # VPN[1] * PTESIZE.
# This gives the physical address of the page table entry. add t2, t0, t2 # a + VPN[1] * PTESIZE.
srl t2, a0, t1
and t2, t2, t5 # VPN[i] * PTESIZE.
add t2, t0, t2 # a + VPN[i] * PTESIZE.
beqz a3, .Limem_map_at_leaf
lw t3, (t2) lw t3, (t2)
andi t6, t3, 0b1 andi t4, t3, 0b1
beqz t6, .Limem_map_at_create beqz t4, .Limem_map_at_create
li t4, 0xfffffc00
and t0, t3, t4 and t0, t3, t4
slli t0, t0, 2 slli t0, t0, 2
j .Limem_map_at_next j .Limem_map_at_existing
.Limem_map_at_create: .Limem_map_at_create:
# Take a chunk of free memory and use it as the next page table. # Take a chunk of free memory and use it as the next page table.
# The beginning addres off the chunk is the base address (a) for the next level. # The beginning addres off the chunk is the base address (a) for the next level.
mv t0, a2 mv t0, a0
srli t3, t0, 2 srli t3, t0, 2
ori t3, t3, 0b1 ori t3, t3, 0b1
sw t3, (t2) sw t3, (t2)
.Limem_map_at_next: li t4, PAGE_SIZE
# Calculate the next page table address for the next level. add a0, a0, t4
addi t1, t1, -10
addi a3, a3, -1
j .Limem_map_at_loop .Limem_map_at_existing:
srli t2, a1, 10
and t2, t2, t1 # VPN[0] * PTESIZE.
add t2, t0, t2 # a + VPN[0] * PTESIZE.
.Limem_map_at_leaf:
srli t3, a1, 2 # Physical page number mapped to 12 bits of the page table entry. srli t3, a1, 2 # Physical page number mapped to 12 bits of the page table entry.
ori a4, a4, 0b1 ori a2, a2, 0b1
or t3, t3, a4 # Execute, write, read and valid. or t3, t3, a2 # Execute, write, read and valid.
sw t3, (t2) sw t3, (t2)
ret ret
.section .text .section .text
@@ -361,7 +357,7 @@ kernel_main:
lw a2, 20(sp) lw a2, 20(sp)
li a3, 0 li a3, 0
li a4, 0b0010 li a4, 0b0010
call imem_map_at call pmem_map_at
lw a0, 16(sp) lw a0, 16(sp)
call device_tree call device_tree