-
Notifications
You must be signed in to change notification settings - Fork 0
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
- Loading branch information
Showing
8 changed files
with
192 additions
and
23 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Some generated files are not rendered by default. Learn more about how customized files appear on GitHub.
Oops, something went wrong.
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,47 @@ | ||
use alloc::alloc::{GlobalAlloc, Layout}; | ||
use x86_64::{structures::paging::Page, VirtAddr}; | ||
use core::ptr::null_mut; | ||
use x86_64::structures::paging::Size4KiB; | ||
use crate::memory; | ||
use x86_64::structures::paging::FrameAllocator; | ||
use x86_64::structures::paging::mapper::{MapToError, Mapper}; | ||
use x86_64::structures::paging::PageTableFlags as Flags; | ||
use linked_list_allocator::LockedHeap; | ||
pub const HEAP_START: u64 = 0x4444_4444_0000; | ||
pub const HEAP_SIZE: u64 = 100 * 1024; // 100 KiB | ||
|
||
pub struct Dummy; | ||
|
||
unsafe impl GlobalAlloc for Dummy { | ||
unsafe fn alloc(&self, _layout: Layout) -> *mut u8 { | ||
null_mut() | ||
} | ||
|
||
unsafe fn dealloc(&self, _ptr: *mut u8, _layout: Layout) { | ||
panic!("dealloc is not supported") | ||
} | ||
} | ||
|
||
#[global_allocator] | ||
static ALLOCATOR: LockedHeap = LockedHeap::empty(); | ||
|
||
pub fn init_heap(mapper: &mut impl Mapper<Size4KiB>, frame_allocator: &mut impl FrameAllocator<Size4KiB>) -> Result<(), MapToError<Size4KiB>> { | ||
|
||
let page_range = { | ||
let heap_start = VirtAddr::new(HEAP_START as u64); | ||
let heap_end = heap_start + HEAP_SIZE - 1u64; | ||
let heap_start_page: Page<Size4KiB> = Page::containing_address(heap_start); | ||
let heap_end_page: Page<Size4KiB> = Page::containing_address(heap_end); | ||
Page::range_inclusive(heap_start_page, heap_end_page) | ||
}; | ||
for page in page_range { | ||
let frame = frame_allocator.allocate_frame().ok_or(MapToError::FrameAllocationFailed)?; | ||
let flags = Flags::PRESENT | Flags::WRITABLE; | ||
unsafe { mapper.map_to(page, frame, flags, frame_allocator)?.flush() }; | ||
|
||
} | ||
unsafe { | ||
ALLOCATOR.lock().init(HEAP_START as usize, HEAP_SIZE as usize); | ||
} | ||
Ok(()) | ||
} |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,67 @@ | ||
#![no_std] | ||
#![no_main] | ||
#![feature(custom_test_frameworks)] | ||
#![test_runner(candy::test_runner)] | ||
#![reexport_test_harness_main = "test_main"] | ||
|
||
extern crate alloc; | ||
|
||
use bootloader::{entry_point, BootInfo}; | ||
use core::panic::PanicInfo; | ||
|
||
entry_point!(main); | ||
|
||
fn main(boot_info: &'static BootInfo) -> ! { | ||
use candy::allocator; | ||
use candy::memory::{self, BootInfoFrameAllocator}; | ||
use x86_64::VirtAddr; | ||
|
||
candy::init(); | ||
let phys_mem_offset = VirtAddr::new(boot_info.physical_memory_offset); | ||
let mut mapper = unsafe { memory::init(phys_mem_offset) }; | ||
let mut frame_allocator = unsafe { | ||
BootInfoFrameAllocator::init(&boot_info.memory_map) | ||
}; | ||
allocator::init_heap(&mut mapper, &mut frame_allocator) | ||
.expect("heap initialization failed"); | ||
|
||
test_main(); | ||
loop {} | ||
} | ||
|
||
#[panic_handler] | ||
fn panic(info: &PanicInfo) -> ! { | ||
candy::test_panic_handler(info) | ||
} | ||
|
||
use alloc::boxed::Box; | ||
|
||
#[test_case] | ||
fn simple_allocation() { | ||
let heap_value_1 = Box::new(41); | ||
let heap_value_2 = Box::new(13); | ||
assert_eq!(*heap_value_1, 41); | ||
assert_eq!(*heap_value_2, 13); | ||
} | ||
|
||
use alloc::vec::Vec; | ||
|
||
#[test_case] | ||
fn large_vec() { | ||
let n = 1000; | ||
let mut vec = Vec::new(); | ||
for i in 0..n { | ||
vec.push(i); | ||
} | ||
assert_eq!(vec.iter().sum::<u64>(), (n - 1) * n / 2); | ||
} | ||
|
||
use candy::allocator::HEAP_SIZE; | ||
|
||
#[test_case] | ||
fn many_boxes() { | ||
for i in 0..HEAP_SIZE { | ||
let x = Box::new(i); | ||
assert_eq!(*x, i); | ||
} | ||
} |