From 29a15ecc295f7b0d830c8f1cf0f9f695c21c35f9 Mon Sep 17 00:00:00 2001 From: Hiroki Tokunaga Date: Sun, 13 Jun 2021 21:25:46 +0900 Subject: [PATCH 1/2] chore: mark `ElfLoader::load` as unsafe This method assumes that the memory is allocated by `ElfLoader::allocate`, but the compiler can't ensure it. Without it, the program may violate memory safety by e.g., modifying memory used by others. --- src/lib.rs | 21 ++++++++++++++------- 1 file changed, 14 insertions(+), 7 deletions(-) diff --git a/src/lib.rs b/src/lib.rs index 4b7bdc2..6c8426f 100644 --- a/src/lib.rs +++ b/src/lib.rs @@ -227,9 +227,13 @@ pub trait ElfLoader { fn allocate(&mut self, load_headers: LoadableHeaders) -> Result<(), ElfLoaderErr>; /// Copies `region` into memory starting at `base`. - /// The caller makes sure that there was an `allocate` call previously + /// + /// # Safety + /// + /// The caller must ensure that there was an `allocate` call previously /// to initialize the region. - fn load(&mut self, flags: Flags, base: VAddr, region: &[u8]) -> Result<(), ElfLoaderErr>; + unsafe fn load(&mut self, flags: Flags, base: VAddr, region: &[u8]) + -> Result<(), ElfLoaderErr>; /// Request for the client to relocate the given `entry` /// within the loaded ELF file. @@ -465,11 +469,14 @@ impl<'s> ElfBinary<'s> { if let Ph64(header) = p { let typ = header.get_type()?; if typ == Type::Load { - loader.load( - header.flags, - header.virtual_addr, - header.raw_data(&self.file), - )?; + // SAFETY: Yes, `loader.allocate(load_iter)?;` allocates memory. + unsafe { + loader.load( + header.flags, + header.virtual_addr, + header.raw_data(&self.file), + )?; + } } else if typ == Type::Tls { loader.tls( header.virtual_addr, From 61c469a971362963bee341a1df9a4ac42ac1408c Mon Sep 17 00:00:00 2001 From: Hiroki Tokunaga Date: Sun, 13 Jun 2021 21:40:40 +0900 Subject: [PATCH 2/2] fix: test --- src/lib.rs | 7 ++++++- 1 file changed, 6 insertions(+), 1 deletion(-) diff --git a/src/lib.rs b/src/lib.rs index 6c8426f..1c7204b 100644 --- a/src/lib.rs +++ b/src/lib.rs @@ -592,7 +592,12 @@ mod test { } } - fn load(&mut self, _flags: Flags, base: VAddr, region: &[u8]) -> Result<(), ElfLoaderErr> { + unsafe fn load( + &mut self, + _flags: Flags, + base: VAddr, + region: &[u8], + ) -> Result<(), ElfLoaderErr> { info!("load base = {:#x} size = {:#x} region", base, region.len()); self.actions.push(LoaderAction::Load(base, region.len())); Ok(())