forked from Bananymous/banan-os
Bootloader: Implement better memset and memcpy for 32 bit addresses
This commit is contained in:
parent
0e405755ad
commit
9ac3f48fcb
|
@ -15,5 +15,6 @@ set(BOOTLOADER_SOURCES
|
||||||
)
|
)
|
||||||
|
|
||||||
add_executable(bootloader ${BOOTLOADER_SOURCES})
|
add_executable(bootloader ${BOOTLOADER_SOURCES})
|
||||||
|
include_directories(${CMAKE_CURRENT_SOURCE_DIR})
|
||||||
target_link_options(bootloader PRIVATE LINKER:-T,${CMAKE_CURRENT_SOURCE_DIR}/linker.ld)
|
target_link_options(bootloader PRIVATE LINKER:-T,${CMAKE_CURRENT_SOURCE_DIR}/linker.ld)
|
||||||
target_link_options(bootloader PRIVATE -nostdlib)
|
target_link_options(bootloader PRIVATE -nostdlib)
|
||||||
|
|
|
@ -1,3 +1,5 @@
|
||||||
|
.include "common.S"
|
||||||
|
|
||||||
.code16
|
.code16
|
||||||
|
|
||||||
#########################################
|
#########################################
|
||||||
|
@ -103,12 +105,12 @@ stage2_main:
|
||||||
movl %edx, %cr0
|
movl %edx, %cr0
|
||||||
|
|
||||||
# jump to protected mode
|
# jump to protected mode
|
||||||
ljmpl $0x18, $protected_mode
|
ljmpl $GDT_CODE32, $protected_mode
|
||||||
|
|
||||||
.code32
|
.code32
|
||||||
protected_mode:
|
protected_mode:
|
||||||
# setup protected mode segments
|
# setup protected mode segments
|
||||||
movw $0x10, %dx
|
movw $GDT_DATA32, %dx
|
||||||
movw %dx, %ds
|
movw %dx, %ds
|
||||||
movw %dx, %es
|
movw %dx, %es
|
||||||
movw %dx, %fs
|
movw %dx, %fs
|
||||||
|
@ -127,15 +129,15 @@ enter_unreal_mode:
|
||||||
movl %cr0, %eax
|
movl %cr0, %eax
|
||||||
orb $1, %al
|
orb $1, %al
|
||||||
movl %eax, %cr0
|
movl %eax, %cr0
|
||||||
ljmpl $0x8, $.enter_unreal_mode_pmode
|
ljmpl $GDT_CODE16, $.enter_unreal_mode_pmode
|
||||||
|
|
||||||
.enter_unreal_mode_pmode:
|
.enter_unreal_mode_pmode:
|
||||||
movw $0x10, %bx
|
movw $GDT_DATA32, %bx
|
||||||
movw %bx, %ds
|
movw %bx, %ds
|
||||||
|
|
||||||
andb $0xFE, %al
|
andb $0xFE, %al
|
||||||
movl %eax, %cr0
|
movl %eax, %cr0
|
||||||
ljmpl $0x0, $.enter_unreal_mode_unreal
|
ljmpl $0x00, $.enter_unreal_mode_unreal
|
||||||
|
|
||||||
.enter_unreal_mode_unreal:
|
.enter_unreal_mode_unreal:
|
||||||
popw %ds
|
popw %ds
|
||||||
|
|
|
@ -0,0 +1,3 @@
|
||||||
|
.set GDT_CODE16, 0x08
|
||||||
|
.set GDT_DATA32, 0x10
|
||||||
|
.set GDT_CODE32, 0x18
|
|
@ -113,24 +113,6 @@ elf_validate_file_header:
|
||||||
movw $elf_validate_file_header_not_executable_msg, %si
|
movw $elf_validate_file_header_not_executable_msg, %si
|
||||||
jmp print_and_halt
|
jmp print_and_halt
|
||||||
|
|
||||||
|
|
||||||
# sets memory to zero
|
|
||||||
# edi: start address
|
|
||||||
# ecx: byte count
|
|
||||||
# on return
|
|
||||||
# edi: start address + byte count
|
|
||||||
# ecx: 0
|
|
||||||
elf_memset_zero:
|
|
||||||
test %ecx, %ecx
|
|
||||||
jz .elf_memset_zero_done
|
|
||||||
.elf_memset_zero_loop:
|
|
||||||
movb $0, (%edi)
|
|
||||||
incl %edi
|
|
||||||
decl %ecx
|
|
||||||
jnz .elf_memset_zero_loop
|
|
||||||
.elf_memset_zero_done:
|
|
||||||
ret
|
|
||||||
|
|
||||||
# reads memory specified by 32 bit elf_program_header to memory
|
# reads memory specified by 32 bit elf_program_header to memory
|
||||||
elf_read_program_header32_to_memory:
|
elf_read_program_header32_to_memory:
|
||||||
pushal
|
pushal
|
||||||
|
@ -144,7 +126,7 @@ elf_read_program_header32_to_memory:
|
||||||
addl %ebx, %edi
|
addl %ebx, %edi
|
||||||
movl (elf_program_header + p32_memsz), %ecx
|
movl (elf_program_header + p32_memsz), %ecx
|
||||||
subl %ebx, %ecx
|
subl %ebx, %ecx
|
||||||
call elf_memset_zero
|
xorb %al, %al; call memset32
|
||||||
|
|
||||||
# read file specified in program header to memory
|
# read file specified in program header to memory
|
||||||
movl (elf_program_header + p32_offset), %eax
|
movl (elf_program_header + p32_offset), %eax
|
||||||
|
@ -171,7 +153,7 @@ elf_read_program_header64_to_memory:
|
||||||
addl %ebx, %edi
|
addl %ebx, %edi
|
||||||
movl (elf_program_header + p64_memsz), %ecx
|
movl (elf_program_header + p64_memsz), %ecx
|
||||||
subl %ebx, %ecx
|
subl %ebx, %ecx
|
||||||
call elf_memset_zero
|
xorb %al, %al; call memset32
|
||||||
|
|
||||||
# read file specified in program header to memory
|
# read file specified in program header to memory
|
||||||
movl (elf_program_header + p64_offset), %eax
|
movl (elf_program_header + p64_offset), %eax
|
||||||
|
|
|
@ -454,15 +454,7 @@ ext2_inode_read_bytes:
|
||||||
movl $ext2_block_buffer, %esi
|
movl $ext2_block_buffer, %esi
|
||||||
addl %edx, %esi
|
addl %edx, %esi
|
||||||
|
|
||||||
# very dumb memcpy with 32 bit addresses
|
call memcpy32
|
||||||
xorl %ebx, %ebx
|
|
||||||
.ext2_inode_read_bytes_memcpy_partial:
|
|
||||||
movb (%esi, %ebx), %al
|
|
||||||
movb %al, (%edi, %ebx)
|
|
||||||
incl %ebx
|
|
||||||
decl %ecx
|
|
||||||
jnz .ext2_inode_read_bytes_memcpy_partial
|
|
||||||
addl %ebx, %edi
|
|
||||||
|
|
||||||
# check if all sectors are read
|
# check if all sectors are read
|
||||||
cmpl $0, 4(%esp)
|
cmpl $0, 4(%esp)
|
||||||
|
@ -487,16 +479,8 @@ ext2_inode_read_bytes:
|
||||||
addl %ecx, 0(%esp)
|
addl %ecx, 0(%esp)
|
||||||
subl %ecx, 4(%esp)
|
subl %ecx, 4(%esp)
|
||||||
|
|
||||||
# very dumb memcpy with 32 bit addresses
|
|
||||||
movl $ext2_block_buffer, %esi
|
movl $ext2_block_buffer, %esi
|
||||||
movl $0, %ebx
|
call memcpy32
|
||||||
.ext2_inode_read_bytes_memcpy:
|
|
||||||
movb (%esi, %ebx), %al
|
|
||||||
movb %al, (%edi, %ebx)
|
|
||||||
incl %ebx
|
|
||||||
decl %ecx
|
|
||||||
jnz .ext2_inode_read_bytes_memcpy
|
|
||||||
addl %ebx, %edi
|
|
||||||
|
|
||||||
# read next block if more sectors remaining
|
# read next block if more sectors remaining
|
||||||
cmpl $0, 4(%esp)
|
cmpl $0, 4(%esp)
|
||||||
|
|
|
@ -1,3 +1,5 @@
|
||||||
|
.include "common.S"
|
||||||
|
|
||||||
.set SCREEN_WIDTH, 80
|
.set SCREEN_WIDTH, 80
|
||||||
.set SCREEN_HEIGHT, 25
|
.set SCREEN_HEIGHT, 25
|
||||||
|
|
||||||
|
@ -273,6 +275,127 @@ isprint:
|
||||||
movb $0, %al
|
movb $0, %al
|
||||||
ret
|
ret
|
||||||
|
|
||||||
|
|
||||||
|
# memset with 32 bit registers
|
||||||
|
# edi: destination address
|
||||||
|
# ecx: bytes count
|
||||||
|
# al: value to set
|
||||||
|
# return:
|
||||||
|
# edi: destination address + bytes count
|
||||||
|
# ecx: 0
|
||||||
|
# other: preserved
|
||||||
|
.global memset32
|
||||||
|
memset32:
|
||||||
|
testl %ecx, %ecx
|
||||||
|
jz .memset32_done
|
||||||
|
|
||||||
|
pushf; cli
|
||||||
|
pushw %es
|
||||||
|
pushl %eax
|
||||||
|
pushl %ebx
|
||||||
|
pushl %edx
|
||||||
|
|
||||||
|
movl %cr0, %ebx
|
||||||
|
orb $1, %bl
|
||||||
|
movl %ebx, %cr0
|
||||||
|
|
||||||
|
ljmpl $GDT_CODE32, $.memset32_pmode32
|
||||||
|
|
||||||
|
.code32
|
||||||
|
.memset32_pmode32:
|
||||||
|
movw $GDT_DATA32, %dx
|
||||||
|
movw %dx, %es
|
||||||
|
|
||||||
|
movl %ecx, %edx
|
||||||
|
|
||||||
|
andl $3, %ecx
|
||||||
|
rep stosb %es:(%edi)
|
||||||
|
|
||||||
|
movl %edx, %ecx
|
||||||
|
shrl $2, %ecx
|
||||||
|
|
||||||
|
movb %al, %ah
|
||||||
|
movw %ax, %dx
|
||||||
|
shll $16, %eax
|
||||||
|
movw %dx, %ax
|
||||||
|
rep stosl %es:(%edi)
|
||||||
|
|
||||||
|
ljmpl $GDT_CODE16, $.memset32_pmode16
|
||||||
|
|
||||||
|
.code16
|
||||||
|
.memset32_pmode16:
|
||||||
|
andb $0xFE, %bl
|
||||||
|
movl %ebx, %cr0
|
||||||
|
ljmpl $0x00, $.memset32_rmode16
|
||||||
|
|
||||||
|
.memset32_rmode16:
|
||||||
|
popl %edx
|
||||||
|
popl %ebx
|
||||||
|
popl %eax
|
||||||
|
popw %es
|
||||||
|
popf
|
||||||
|
|
||||||
|
.memset32_done:
|
||||||
|
ret
|
||||||
|
|
||||||
|
# memcpy with 32 bit registers
|
||||||
|
# esi: source address
|
||||||
|
# edi: destination address
|
||||||
|
# ecx: bytes count
|
||||||
|
# return:
|
||||||
|
# esi: source address + bytes count
|
||||||
|
# edi: destination address + bytes count
|
||||||
|
# ecx: 0
|
||||||
|
# other: preserved
|
||||||
|
.global memcpy32
|
||||||
|
memcpy32:
|
||||||
|
testl %ecx, %ecx
|
||||||
|
jz .memcpy32_done
|
||||||
|
|
||||||
|
pushf; cli
|
||||||
|
pushw %ds
|
||||||
|
pushw %es
|
||||||
|
pushl %ebx
|
||||||
|
pushl %edx
|
||||||
|
|
||||||
|
movl %cr0, %ebx
|
||||||
|
orb $1, %bl
|
||||||
|
movl %ebx, %cr0
|
||||||
|
|
||||||
|
ljmpl $GDT_CODE32, $.memcpy32_pmode32
|
||||||
|
|
||||||
|
.code32
|
||||||
|
.memcpy32_pmode32:
|
||||||
|
movw $GDT_DATA32, %dx
|
||||||
|
movw %dx, %ds
|
||||||
|
movw %dx, %es
|
||||||
|
|
||||||
|
movl %ecx, %edx
|
||||||
|
andl $3, %ecx
|
||||||
|
rep movsb %ds:(%esi), %es:(%edi)
|
||||||
|
|
||||||
|
movl %edx, %ecx
|
||||||
|
shrl $2, %ecx
|
||||||
|
rep movsl %ds:(%esi), %es:(%edi)
|
||||||
|
|
||||||
|
ljmpl $GDT_CODE16, $.memcpy32_pmode16
|
||||||
|
|
||||||
|
.code16
|
||||||
|
.memcpy32_pmode16:
|
||||||
|
andb $0xFE, %bl
|
||||||
|
movl %ebx, %cr0
|
||||||
|
ljmpl $0x00, $.memcpy32_rmode16
|
||||||
|
|
||||||
|
.memcpy32_rmode16:
|
||||||
|
popl %edx
|
||||||
|
popl %ebx
|
||||||
|
popw %es
|
||||||
|
popw %ds
|
||||||
|
popf
|
||||||
|
|
||||||
|
.memcpy32_done:
|
||||||
|
ret
|
||||||
|
|
||||||
.section .bss
|
.section .bss
|
||||||
|
|
||||||
# enough for base 2 printing
|
# enough for base 2 printing
|
||||||
|
|
Loading…
Reference in New Issue