Skip to content

Commit

Permalink
kernel/task: Remove p_vaddr alignment requirement from exec_user()
Browse files Browse the repository at this point in the history
Elf spec doesn't require `p_vaddr` to be page aligned, so remove this
requirment and handle unaligned virtual start address in exec_user().

Signed-off-by: Vijay Dhanraj <[email protected]>
Signed-off-by: Joerg Roedel <[email protected]>
  • Loading branch information
vijaydhanraj authored and joergroedel committed Nov 27, 2024
1 parent d3fa746 commit 7367154
Showing 1 changed file with 18 additions and 5 deletions.
23 changes: 18 additions & 5 deletions kernel/src/task/exec.rs
Original file line number Diff line number Diff line change
Expand Up @@ -11,6 +11,7 @@ use crate::mm::vm::VMFileMappingFlags;
use crate::mm::USER_MEM_END;
use crate::task::{create_user_task, current_task, schedule};
use crate::types::PAGE_SIZE;
use crate::utils::align_up;
use elf::{Elf64File, Elf64PhdrFlags};

fn convert_elf_phdr_flags(flags: Elf64PhdrFlags) -> VMFileMappingFlags {
Expand Down Expand Up @@ -53,14 +54,26 @@ pub fn exec_user(binary: &str) -> Result<(), SvsmError> {
let virt_end = VirtAddr::from(seg.vaddr_range.vaddr_end).align_up(PAGE_SIZE);
let file_offset = seg.file_range.offset_begin;
let len = virt_end - virt_start;
let file_size = seg.file_range.offset_end - seg.file_range.offset_begin;
let flags = convert_elf_phdr_flags(seg.flags);

if !virt_start.is_aligned(PAGE_SIZE) {
return Err(SvsmError::Mem);
}

if file_offset > 0 {
task.mmap_user(virt_start, Some(&fh), file_offset, len, flags)?;
if file_size > len {
return Err(SvsmError::Elf(elf::ElfError::InvalidFileRange));
}

// Handle unaligned VirtAddr and Offset
let start_aligned = virt_start.page_align();
let offset = file_offset - virt_start.page_offset();
let size = file_size + virt_start.page_offset();
task.mmap_user(start_aligned, Some(&fh), offset, size, flags)?;

let size_aligned = align_up(size, PAGE_SIZE);
if size_aligned < len {
let start_anon = start_aligned.const_add(size_aligned);
let remaining_len = len - size_aligned;
task.mmap_user(start_anon, None, 0, remaining_len, flags)?;
}
} else {
task.mmap_user(virt_start, None, 0, len, flags)?;
}
Expand Down

0 comments on commit 7367154

Please sign in to comment.