diff --git a/src/main.rs b/src/main.rs index b2e2736..a6a9474 100644 --- a/src/main.rs +++ b/src/main.rs @@ -500,33 +500,62 @@ pub extern "C" fn main() -> ! { print!("live: 0/{} MiB", size / MIBI as u64); - let ptr = os.alloc_zeroed_page_aligned(size as usize); - if ptr.is_null() { - panic!("Failed to allocate memory for live"); - } - - let live = unsafe { slice::from_raw_parts_mut(ptr, size as usize) }; - - let mut i = 0; - for chunk in live.chunks_mut(MIBI) { - print!("\rlive: {}/{} MiB", i / MIBI as u64, size / MIBI as u64); - i += unsafe { - fs.disk - .read_at(fs.block + i / redoxfs::BLOCK_SIZE, chunk) - .expect("Failed to read live disk") as u64 - }; - } - println!("\rlive: {}/{} MiB", i / MIBI as u64, size / MIBI as u64); - - println!("Switching to live disk"); - unsafe { - LIVE_OPT = Some((fs.block, slice::from_raw_parts_mut(ptr, size as usize))); - } + let live_size = match usize::try_from(size) { + Ok(live_size) => live_size, + Err(_) => { + println!("\rlive: disabled (image too large for bootloader address space)"); + live = false; + 0 + } + }; - area_add(OsMemoryEntry { - base: live.as_ptr() as u64, - size: live.len() as u64, - kind: OsMemoryKind::Reserved, - }); + let ptr = if live { + os.alloc_zeroed_page_aligned(live_size) + } else { + ptr::null_mut() + }; + + if live && ptr.is_null() { + println!( + "\rlive: disabled (unable to allocate {} MiB upfront)", + size / MIBI as u64 + ); + live = false; + } + + let live = if live { + Some(unsafe { slice::from_raw_parts_mut(ptr, live_size) }) + } else { + println!("Continuing without live preload"); + None + }; + + if let Some(live) = live { + let mut i = 0; + for chunk in live.chunks_mut(MIBI) { + print!("\rlive: {}/{} MiB", i / MIBI as u64, size / MIBI as u64); + i += unsafe { + fs.disk + .read_at(fs.block + i / redoxfs::BLOCK_SIZE, chunk) + .expect("Failed to read live disk") as u64 + }; + } + println!("\rlive: {}/{} MiB", i / MIBI as u64, size / MIBI as u64); + + println!("Switching to live disk"); + unsafe { + LIVE_OPT = Some((fs.block, slice::from_raw_parts_mut(ptr, live_size))); + } + + area_add(OsMemoryEntry { + base: live.as_ptr() as u64, + size: live.len() as u64, + kind: OsMemoryKind::Reserved, + }); + + Some(live) + } else { + None + } - - Some(live) } else { None };