mirror of
https://github.com/asterinas/asterinas.git
synced 2025-06-25 02:13:24 +00:00
Return correct error type if executing a file that is not executable
This commit is contained in:
committed by
Tate, Hongliang Tian
parent
3f15bcaf5d
commit
8aef80f978
@ -45,6 +45,10 @@ impl InodeType {
|
|||||||
pub fn is_reguler_file(&self) -> bool {
|
pub fn is_reguler_file(&self) -> bool {
|
||||||
*self == InodeType::File
|
*self == InodeType::File
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub fn is_directory(&self) -> bool {
|
||||||
|
*self == InodeType::Dir
|
||||||
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
impl From<DeviceType> for InodeType {
|
impl From<DeviceType> for InodeType {
|
||||||
|
@ -35,7 +35,7 @@ pub fn load_program_to_root_vmar(
|
|||||||
};
|
};
|
||||||
if let Some(mut new_argv) = parse_shebang_line(&*file_header)? {
|
if let Some(mut new_argv) = parse_shebang_line(&*file_header)? {
|
||||||
if recursion_limit == 0 {
|
if recursion_limit == 0 {
|
||||||
return_errno_with_message!(Errno::EINVAL, "the recursieve limit is reached");
|
return_errno_with_message!(Errno::ELOOP, "the recursieve limit is reached");
|
||||||
}
|
}
|
||||||
new_argv.extend_from_slice(&argv);
|
new_argv.extend_from_slice(&argv);
|
||||||
let interpreter = {
|
let interpreter = {
|
||||||
@ -43,6 +43,7 @@ pub fn load_program_to_root_vmar(
|
|||||||
let fs_path = FsPath::new(AT_FDCWD, &filename)?;
|
let fs_path = FsPath::new(AT_FDCWD, &filename)?;
|
||||||
fs_resolver.lookup(&fs_path)?
|
fs_resolver.lookup(&fs_path)?
|
||||||
};
|
};
|
||||||
|
check_executable_file(&interpreter)?;
|
||||||
return load_program_to_root_vmar(
|
return load_program_to_root_vmar(
|
||||||
root_vmar,
|
root_vmar,
|
||||||
interpreter,
|
interpreter,
|
||||||
@ -56,3 +57,19 @@ pub fn load_program_to_root_vmar(
|
|||||||
load_elf_to_root_vmar(root_vmar, &*file_header, elf_file, fs_resolver, argv, envp)?;
|
load_elf_to_root_vmar(root_vmar, &*file_header, elf_file, fs_resolver, argv, envp)?;
|
||||||
Ok((abs_path, elf_load_info))
|
Ok((abs_path, elf_load_info))
|
||||||
}
|
}
|
||||||
|
|
||||||
|
pub fn check_executable_file(dentry: &Arc<Dentry>) -> Result<()> {
|
||||||
|
if dentry.inode_type().is_directory() {
|
||||||
|
return_errno_with_message!(Errno::EISDIR, "the file is a directory");
|
||||||
|
}
|
||||||
|
|
||||||
|
if !dentry.inode_type().is_reguler_file() {
|
||||||
|
return_errno_with_message!(Errno::EACCES, "the dentry is not a regular file");
|
||||||
|
}
|
||||||
|
|
||||||
|
if !dentry.inode_mode().is_executable() {
|
||||||
|
return_errno_with_message!(Errno::EACCES, "the dentry is not executable");
|
||||||
|
}
|
||||||
|
|
||||||
|
Ok(())
|
||||||
|
}
|
||||||
|
@ -8,7 +8,7 @@ use crate::log_syscall_entry;
|
|||||||
use crate::prelude::*;
|
use crate::prelude::*;
|
||||||
use crate::process::posix_thread::name::ThreadName;
|
use crate::process::posix_thread::name::ThreadName;
|
||||||
use crate::process::posix_thread::posix_thread_ext::PosixThreadExt;
|
use crate::process::posix_thread::posix_thread_ext::PosixThreadExt;
|
||||||
use crate::process::program_loader::load_program_to_root_vmar;
|
use crate::process::program_loader::{check_executable_file, load_program_to_root_vmar};
|
||||||
use crate::syscall::{SYS_EXECVE, SYS_EXECVEAT};
|
use crate::syscall::{SYS_EXECVE, SYS_EXECVEAT};
|
||||||
use crate::util::{read_cstring_from_user, read_val_from_user};
|
use crate::util::{read_cstring_from_user, read_val_from_user};
|
||||||
|
|
||||||
@ -19,13 +19,11 @@ pub fn sys_execve(
|
|||||||
context: &mut UserContext,
|
context: &mut UserContext,
|
||||||
) -> Result<SyscallReturn> {
|
) -> Result<SyscallReturn> {
|
||||||
log_syscall_entry!(SYS_EXECVE);
|
log_syscall_entry!(SYS_EXECVE);
|
||||||
let executable_path = read_filename(filename_ptr)?;
|
|
||||||
let elf_file = {
|
let elf_file = {
|
||||||
let current = current!();
|
let executable_path = read_filename(filename_ptr)?;
|
||||||
let fs_resolver = current.fs().read();
|
lookup_executable_file(AT_FDCWD, executable_path, OpenFlags::empty())?
|
||||||
let fs_path = FsPath::new(AT_FDCWD, &executable_path)?;
|
|
||||||
fs_resolver.lookup(&fs_path)?
|
|
||||||
};
|
};
|
||||||
|
|
||||||
do_execve(elf_file, argv_ptr_ptr, envp_ptr_ptr, context)?;
|
do_execve(elf_file, argv_ptr_ptr, envp_ptr_ptr, context)?;
|
||||||
Ok(SyscallReturn::NoReturn)
|
Ok(SyscallReturn::NoReturn)
|
||||||
}
|
}
|
||||||
@ -39,10 +37,13 @@ pub fn sys_execveat(
|
|||||||
context: &mut UserContext,
|
context: &mut UserContext,
|
||||||
) -> Result<SyscallReturn> {
|
) -> Result<SyscallReturn> {
|
||||||
log_syscall_entry!(SYS_EXECVEAT);
|
log_syscall_entry!(SYS_EXECVEAT);
|
||||||
|
|
||||||
|
let elf_file = {
|
||||||
let flags = OpenFlags::from_bits_truncate(flags);
|
let flags = OpenFlags::from_bits_truncate(flags);
|
||||||
let filename = read_filename(filename_ptr)?;
|
let filename = read_filename(filename_ptr)?;
|
||||||
let elf_file = lookup_executable_file(dfd, filename, flags)?;
|
lookup_executable_file(dfd, filename, flags)?
|
||||||
check_file_type_and_permission(&elf_file)?;
|
};
|
||||||
|
|
||||||
do_execve(elf_file, argv_ptr_ptr, envp_ptr_ptr, context)?;
|
do_execve(elf_file, argv_ptr_ptr, envp_ptr_ptr, context)?;
|
||||||
Ok(SyscallReturn::NoReturn)
|
Ok(SyscallReturn::NoReturn)
|
||||||
}
|
}
|
||||||
@ -68,22 +69,10 @@ fn lookup_executable_file(
|
|||||||
fs_resolver.lookup(&fs_path)
|
fs_resolver.lookup(&fs_path)
|
||||||
}
|
}
|
||||||
}?;
|
}?;
|
||||||
check_file_type_and_permission(&dentry)?;
|
check_executable_file(&dentry)?;
|
||||||
Ok(dentry)
|
Ok(dentry)
|
||||||
}
|
}
|
||||||
|
|
||||||
fn check_file_type_and_permission(dentry: &Arc<Dentry>) -> Result<()> {
|
|
||||||
if !dentry.inode_type().is_reguler_file() {
|
|
||||||
return_errno_with_message!(Errno::EACCES, "the dentry is not a regular file");
|
|
||||||
}
|
|
||||||
|
|
||||||
if !dentry.inode_mode().is_executable() {
|
|
||||||
return_errno_with_message!(Errno::EACCES, "the dentry is not executable");
|
|
||||||
}
|
|
||||||
|
|
||||||
Ok(())
|
|
||||||
}
|
|
||||||
|
|
||||||
fn do_execve(
|
fn do_execve(
|
||||||
elf_file: Arc<Dentry>,
|
elf_file: Arc<Dentry>,
|
||||||
argv_ptr_ptr: Vaddr,
|
argv_ptr_ptr: Vaddr,
|
||||||
|
Reference in New Issue
Block a user