mirror of
https://github.com/asterinas/asterinas.git
synced 2025-06-27 03:13:23 +00:00
Move FS things to PosixThread
This commit is contained in:
committed by
Tate, Hongliang Tian
parent
fe7e4884c9
commit
36fc1d3757
@ -18,7 +18,7 @@ use super::{
|
||||
use crate::{
|
||||
cpu::LinuxAbi,
|
||||
current_userspace,
|
||||
fs::{file_table::FileTable, fs_resolver::FsResolver, utils::FileCreationMask},
|
||||
fs::{file_table::FileTable, thread_info::ThreadFsInfo},
|
||||
prelude::*,
|
||||
process::posix_thread::allocate_posix_tid,
|
||||
thread::{AsThread, Tid},
|
||||
@ -213,15 +213,6 @@ fn clone_child_task(
|
||||
);
|
||||
}
|
||||
|
||||
// This is valid combination in Linux. But we do not support it yet.
|
||||
if !clone_flags.contains(CloneFlags::CLONE_FILES) || !clone_flags.contains(CloneFlags::CLONE_FS)
|
||||
{
|
||||
return_errno_with_message!(
|
||||
Errno::EINVAL,
|
||||
"`CLONE_THREAD` without `CLONE_FILES` or `CLONE_FS` is not supported"
|
||||
);
|
||||
}
|
||||
|
||||
let Context {
|
||||
process,
|
||||
posix_thread,
|
||||
@ -232,6 +223,12 @@ fn clone_child_task(
|
||||
// clone system V semaphore
|
||||
clone_sysvsem(clone_flags)?;
|
||||
|
||||
// clone file table
|
||||
let child_file_table = clone_files(posix_thread.file_table(), clone_flags);
|
||||
|
||||
// clone fs
|
||||
let child_fs = clone_fs(posix_thread.fs(), clone_flags);
|
||||
|
||||
let child_root_vmar = process.root_vmar();
|
||||
let child_user_space = {
|
||||
let child_vm_space = child_root_vmar.vm_space().clone();
|
||||
@ -257,7 +254,9 @@ fn clone_child_task(
|
||||
|
||||
let thread_builder = PosixThreadBuilder::new(child_tid, child_user_space, credentials)
|
||||
.process(posix_thread.weak_process())
|
||||
.sig_mask(sig_mask);
|
||||
.sig_mask(sig_mask)
|
||||
.file_table(child_file_table)
|
||||
.fs(child_fs);
|
||||
thread_builder.build()
|
||||
};
|
||||
|
||||
@ -307,16 +306,10 @@ fn clone_child_process(
|
||||
};
|
||||
|
||||
// clone file table
|
||||
let child_file_table = clone_files(process.file_table(), clone_flags);
|
||||
let child_file_table = clone_files(posix_thread.file_table(), clone_flags);
|
||||
|
||||
// clone fs
|
||||
let child_fs = clone_fs(process.fs(), clone_flags);
|
||||
|
||||
// clone umask
|
||||
let child_umask = {
|
||||
let parent_umask = process.umask().read().get();
|
||||
Arc::new(RwLock::new(FileCreationMask::new(parent_umask)))
|
||||
};
|
||||
let child_fs = clone_fs(posix_thread.fs(), clone_flags);
|
||||
|
||||
// clone sig dispositions
|
||||
let child_sig_dispositions = clone_sighand(process.sig_dispositions(), clone_flags);
|
||||
@ -345,6 +338,8 @@ fn clone_child_process(
|
||||
PosixThreadBuilder::new(child_tid, child_user_space, credentials)
|
||||
.thread_name(Some(child_thread_name))
|
||||
.sig_mask(child_sig_mask)
|
||||
.file_table(child_file_table)
|
||||
.fs(child_fs)
|
||||
};
|
||||
|
||||
let mut process_builder =
|
||||
@ -353,9 +348,6 @@ fn clone_child_process(
|
||||
process_builder
|
||||
.main_thread_builder(child_thread_builder)
|
||||
.process_vm(child_process_vm)
|
||||
.file_table(child_file_table)
|
||||
.fs(child_fs)
|
||||
.umask(child_umask)
|
||||
.sig_dispositions(child_sig_dispositions)
|
||||
.nice(child_nice);
|
||||
|
||||
@ -460,14 +452,11 @@ fn clone_cpu_context(
|
||||
child_context
|
||||
}
|
||||
|
||||
fn clone_fs(
|
||||
parent_fs: &Arc<RwMutex<FsResolver>>,
|
||||
clone_flags: CloneFlags,
|
||||
) -> Arc<RwMutex<FsResolver>> {
|
||||
fn clone_fs(parent_fs: &Arc<ThreadFsInfo>, clone_flags: CloneFlags) -> Arc<ThreadFsInfo> {
|
||||
if clone_flags.contains(CloneFlags::CLONE_FS) {
|
||||
parent_fs.clone()
|
||||
} else {
|
||||
Arc::new(RwMutex::new(parent_fs.read().clone()))
|
||||
Arc::new(parent_fs.as_ref().clone())
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -41,8 +41,13 @@ pub fn do_exit_group(term_status: TermStatus) {
|
||||
child.enqueue_signal(signal);
|
||||
}
|
||||
|
||||
// Close all files then exit the process
|
||||
let files = current.file_table().lock().close_all();
|
||||
// Close all files then exit the process.
|
||||
//
|
||||
// FIXME: This is obviously wrong in a number of ways, since different threads can have
|
||||
// different file tables, and different processes can share the same file table.
|
||||
let main_thread = current.main_thread().unwrap();
|
||||
let mut files = main_thread.as_posix_thread().unwrap().file_table().lock();
|
||||
files.close_all();
|
||||
drop(files);
|
||||
|
||||
// Move children to the init process
|
||||
|
@ -6,6 +6,7 @@ use ostd::{cpu::CpuSet, task::Task, user::UserSpace};
|
||||
|
||||
use super::{thread_table, PosixThread};
|
||||
use crate::{
|
||||
fs::{file_table::FileTable, thread_info::ThreadFsInfo},
|
||||
prelude::*,
|
||||
process::{
|
||||
posix_thread::name::ThreadName,
|
||||
@ -29,6 +30,8 @@ pub struct PosixThreadBuilder {
|
||||
thread_name: Option<ThreadName>,
|
||||
set_child_tid: Vaddr,
|
||||
clear_child_tid: Vaddr,
|
||||
file_table: Option<Arc<SpinLock<FileTable>>>,
|
||||
fs: Option<Arc<ThreadFsInfo>>,
|
||||
sig_mask: AtomicSigMask,
|
||||
sig_queues: SigQueues,
|
||||
priority: Priority,
|
||||
@ -44,6 +47,8 @@ impl PosixThreadBuilder {
|
||||
thread_name: None,
|
||||
set_child_tid: 0,
|
||||
clear_child_tid: 0,
|
||||
file_table: None,
|
||||
fs: None,
|
||||
sig_mask: AtomicSigMask::new_empty(),
|
||||
sig_queues: SigQueues::new(),
|
||||
priority: Priority::default(),
|
||||
@ -70,6 +75,16 @@ impl PosixThreadBuilder {
|
||||
self
|
||||
}
|
||||
|
||||
pub fn file_table(mut self, file_table: Arc<SpinLock<FileTable>>) -> Self {
|
||||
self.file_table = Some(file_table);
|
||||
self
|
||||
}
|
||||
|
||||
pub fn fs(mut self, fs: Arc<ThreadFsInfo>) -> Self {
|
||||
self.fs = Some(fs);
|
||||
self
|
||||
}
|
||||
|
||||
pub fn sig_mask(mut self, sig_mask: AtomicSigMask) -> Self {
|
||||
self.sig_mask = sig_mask;
|
||||
self
|
||||
@ -89,11 +104,18 @@ impl PosixThreadBuilder {
|
||||
thread_name,
|
||||
set_child_tid,
|
||||
clear_child_tid,
|
||||
file_table,
|
||||
fs,
|
||||
sig_mask,
|
||||
sig_queues,
|
||||
priority,
|
||||
} = self;
|
||||
|
||||
let file_table =
|
||||
file_table.unwrap_or_else(|| Arc::new(SpinLock::new(FileTable::new_with_stdio())));
|
||||
|
||||
let fs = fs.unwrap_or_else(|| Arc::new(ThreadFsInfo::default()));
|
||||
|
||||
Arc::new_cyclic(|weak_task| {
|
||||
let posix_thread = {
|
||||
let prof_clock = ProfClock::new();
|
||||
@ -107,6 +129,8 @@ impl PosixThreadBuilder {
|
||||
set_child_tid: Mutex::new(set_child_tid),
|
||||
clear_child_tid: Mutex::new(clear_child_tid),
|
||||
credentials,
|
||||
file_table,
|
||||
fs,
|
||||
sig_mask,
|
||||
sig_queues,
|
||||
sig_context: Mutex::new(None),
|
||||
|
@ -20,6 +20,7 @@ use super::{
|
||||
};
|
||||
use crate::{
|
||||
events::Observer,
|
||||
fs::{file_table::FileTable, thread_info::ThreadFsInfo},
|
||||
prelude::*,
|
||||
process::signal::constants::SIGCONT,
|
||||
thread::{AsThread, Thread, Tid},
|
||||
@ -58,6 +59,12 @@ pub struct PosixThread {
|
||||
/// Process credentials. At the kernel level, credentials are a per-thread attribute.
|
||||
credentials: Credentials,
|
||||
|
||||
// Files
|
||||
/// File table
|
||||
file_table: Arc<SpinLock<FileTable>>,
|
||||
/// File system
|
||||
fs: Arc<ThreadFsInfo>,
|
||||
|
||||
// Signal
|
||||
/// Blocked signals
|
||||
sig_mask: AtomicSigMask,
|
||||
@ -107,6 +114,14 @@ impl PosixThread {
|
||||
&self.clear_child_tid
|
||||
}
|
||||
|
||||
pub fn file_table(&self) -> &Arc<SpinLock<FileTable>> {
|
||||
&self.file_table
|
||||
}
|
||||
|
||||
pub fn fs(&self) -> &Arc<ThreadFsInfo> {
|
||||
&self.fs
|
||||
}
|
||||
|
||||
/// Get the reference to the signal mask of the thread.
|
||||
///
|
||||
/// Note that while this function offers mutable access to the signal mask,
|
||||
|
@ -8,7 +8,10 @@ use ostd::{
|
||||
|
||||
use super::{builder::PosixThreadBuilder, name::ThreadName, PosixThread};
|
||||
use crate::{
|
||||
fs::fs_resolver::{FsPath, FsResolver, AT_FDCWD},
|
||||
fs::{
|
||||
fs_resolver::{FsPath, AT_FDCWD},
|
||||
thread_info::ThreadFsInfo,
|
||||
},
|
||||
prelude::*,
|
||||
process::{process_vm::ProcessVm, program_loader::load_program_to_vm, Credentials, Process},
|
||||
thread::{AsThread, Thread, Tid},
|
||||
@ -35,22 +38,22 @@ impl AsPosixThread for Task {
|
||||
/// Creates a task for running an executable file.
|
||||
///
|
||||
/// This function should _only_ be used to create the init user task.
|
||||
#[allow(clippy::too_many_arguments)]
|
||||
pub fn create_posix_task_from_executable(
|
||||
tid: Tid,
|
||||
credentials: Credentials,
|
||||
process_vm: &ProcessVm,
|
||||
fs_resolver: &FsResolver,
|
||||
executable_path: &str,
|
||||
process: Weak<Process>,
|
||||
argv: Vec<CString>,
|
||||
envp: Vec<CString>,
|
||||
) -> Result<Arc<Task>> {
|
||||
let elf_file = {
|
||||
let fs = ThreadFsInfo::default();
|
||||
let (_, elf_load_info) = {
|
||||
let fs_resolver = fs.resolver().read();
|
||||
let fs_path = FsPath::new(AT_FDCWD, executable_path)?;
|
||||
fs_resolver.lookup(&fs_path)?
|
||||
let elf_file = fs.resolver().read().lookup(&fs_path)?;
|
||||
load_program_to_vm(process_vm, elf_file, argv, envp, &fs_resolver, 1)?
|
||||
};
|
||||
let (_, elf_load_info) = load_program_to_vm(process_vm, elf_file, argv, envp, fs_resolver, 1)?;
|
||||
|
||||
let vm_space = process_vm.root_vmar().vm_space().clone();
|
||||
let mut cpu_ctx = UserContext::default();
|
||||
@ -60,6 +63,7 @@ pub fn create_posix_task_from_executable(
|
||||
let thread_name = Some(ThreadName::new_from_executable_path(executable_path)?);
|
||||
let thread_builder = PosixThreadBuilder::new(tid, user_space, credentials)
|
||||
.thread_name(thread_name)
|
||||
.process(process);
|
||||
.process(process)
|
||||
.fs(Arc::new(fs));
|
||||
Ok(thread_builder.build())
|
||||
}
|
||||
|
@ -4,7 +4,6 @@
|
||||
|
||||
use super::{Pid, Process};
|
||||
use crate::{
|
||||
fs::{file_table::FileTable, fs_resolver::FsResolver, utils::FileCreationMask},
|
||||
prelude::*,
|
||||
process::{
|
||||
posix_thread::{create_posix_task_from_executable, PosixThreadBuilder},
|
||||
@ -27,9 +26,6 @@ pub struct ProcessBuilder<'a> {
|
||||
argv: Option<Vec<CString>>,
|
||||
envp: Option<Vec<CString>>,
|
||||
process_vm: Option<ProcessVm>,
|
||||
file_table: Option<Arc<SpinLock<FileTable>>>,
|
||||
fs: Option<Arc<RwMutex<FsResolver>>>,
|
||||
umask: Option<Arc<RwLock<FileCreationMask>>>,
|
||||
resource_limits: Option<ResourceLimits>,
|
||||
sig_dispositions: Option<Arc<Mutex<SigDispositions>>>,
|
||||
credentials: Option<Credentials>,
|
||||
@ -46,9 +42,6 @@ impl<'a> ProcessBuilder<'a> {
|
||||
argv: None,
|
||||
envp: None,
|
||||
process_vm: None,
|
||||
file_table: None,
|
||||
fs: None,
|
||||
umask: None,
|
||||
resource_limits: None,
|
||||
sig_dispositions: None,
|
||||
credentials: None,
|
||||
@ -66,21 +59,6 @@ impl<'a> ProcessBuilder<'a> {
|
||||
self
|
||||
}
|
||||
|
||||
pub fn file_table(&mut self, file_table: Arc<SpinLock<FileTable>>) -> &mut Self {
|
||||
self.file_table = Some(file_table);
|
||||
self
|
||||
}
|
||||
|
||||
pub fn fs(&mut self, fs: Arc<RwMutex<FsResolver>>) -> &mut Self {
|
||||
self.fs = Some(fs);
|
||||
self
|
||||
}
|
||||
|
||||
pub fn umask(&mut self, umask: Arc<RwLock<FileCreationMask>>) -> &mut Self {
|
||||
self.umask = Some(umask);
|
||||
self
|
||||
}
|
||||
|
||||
pub fn resource_limits(&mut self, resource_limits: ResourceLimits) -> &mut Self {
|
||||
self.resource_limits = Some(resource_limits);
|
||||
self
|
||||
@ -139,9 +117,6 @@ impl<'a> ProcessBuilder<'a> {
|
||||
argv,
|
||||
envp,
|
||||
process_vm,
|
||||
file_table,
|
||||
fs,
|
||||
umask,
|
||||
resource_limits,
|
||||
sig_dispositions,
|
||||
credentials,
|
||||
@ -150,18 +125,6 @@ impl<'a> ProcessBuilder<'a> {
|
||||
|
||||
let process_vm = process_vm.or_else(|| Some(ProcessVm::alloc())).unwrap();
|
||||
|
||||
let file_table = file_table
|
||||
.or_else(|| Some(Arc::new(SpinLock::new(FileTable::new_with_stdio()))))
|
||||
.unwrap();
|
||||
|
||||
let fs = fs
|
||||
.or_else(|| Some(Arc::new(RwMutex::new(FsResolver::new()))))
|
||||
.unwrap();
|
||||
|
||||
let umask = umask
|
||||
.or_else(|| Some(Arc::new(RwLock::new(FileCreationMask::default()))))
|
||||
.unwrap();
|
||||
|
||||
let resource_limits = resource_limits
|
||||
.or_else(|| Some(ResourceLimits::default()))
|
||||
.unwrap();
|
||||
@ -180,9 +143,6 @@ impl<'a> ProcessBuilder<'a> {
|
||||
threads,
|
||||
executable_path.to_string(),
|
||||
process_vm,
|
||||
fs,
|
||||
file_table,
|
||||
umask,
|
||||
resource_limits,
|
||||
nice,
|
||||
sig_dispositions,
|
||||
@ -197,7 +157,6 @@ impl<'a> ProcessBuilder<'a> {
|
||||
pid,
|
||||
credentials.unwrap(),
|
||||
process.vm(),
|
||||
&process.fs().read(),
|
||||
executable_path,
|
||||
Arc::downgrade(&process),
|
||||
argv.unwrap(),
|
||||
|
@ -18,7 +18,6 @@ use super::{
|
||||
};
|
||||
use crate::{
|
||||
device::tty::open_ntty_as_controlling_terminal,
|
||||
fs::{file_table::FileTable, fs_resolver::FsResolver, utils::FileCreationMask},
|
||||
prelude::*,
|
||||
sched::priority::{AtomicNice, Nice},
|
||||
thread::{AsThread, Thread},
|
||||
@ -81,12 +80,6 @@ pub struct Process {
|
||||
children: Mutex<BTreeMap<Pid, Arc<Process>>>,
|
||||
/// Process group
|
||||
pub(super) process_group: Mutex<Weak<ProcessGroup>>,
|
||||
/// File table
|
||||
file_table: Arc<SpinLock<FileTable>>,
|
||||
/// FsResolver
|
||||
fs: Arc<RwMutex<FsResolver>>,
|
||||
/// umask
|
||||
umask: Arc<RwLock<FileCreationMask>>,
|
||||
/// resource limits
|
||||
resource_limits: Mutex<ResourceLimits>,
|
||||
/// Scheduling priority nice value
|
||||
@ -185,10 +178,6 @@ impl Process {
|
||||
executable_path: String,
|
||||
process_vm: ProcessVm,
|
||||
|
||||
fs: Arc<RwMutex<FsResolver>>,
|
||||
file_table: Arc<SpinLock<FileTable>>,
|
||||
|
||||
umask: Arc<RwLock<FileCreationMask>>,
|
||||
resource_limits: ResourceLimits,
|
||||
nice: Nice,
|
||||
sig_dispositions: Arc<Mutex<SigDispositions>>,
|
||||
@ -209,9 +198,6 @@ impl Process {
|
||||
parent: ParentProcess::new(parent),
|
||||
children: Mutex::new(BTreeMap::new()),
|
||||
process_group: Mutex::new(Weak::new()),
|
||||
file_table,
|
||||
fs,
|
||||
umask,
|
||||
sig_dispositions,
|
||||
parent_death_signal: AtomicSigNum::new_empty(),
|
||||
exit_signal: AtomicSigNum::new_empty(),
|
||||
@ -620,20 +606,6 @@ impl Process {
|
||||
self.process_vm.init_stack_reader()
|
||||
}
|
||||
|
||||
// ************** File system ****************
|
||||
|
||||
pub fn file_table(&self) -> &Arc<SpinLock<FileTable>> {
|
||||
&self.file_table
|
||||
}
|
||||
|
||||
pub fn fs(&self) -> &Arc<RwMutex<FsResolver>> {
|
||||
&self.fs
|
||||
}
|
||||
|
||||
pub fn umask(&self) -> &Arc<RwLock<FileCreationMask>> {
|
||||
&self.umask
|
||||
}
|
||||
|
||||
// ****************** Signal ******************
|
||||
|
||||
pub fn sig_dispositions(&self) -> &Arc<Mutex<SigDispositions>> {
|
||||
@ -742,9 +714,6 @@ mod test {
|
||||
vec![],
|
||||
String::new(),
|
||||
ProcessVm::alloc(),
|
||||
Arc::new(RwMutex::new(FsResolver::new())),
|
||||
Arc::new(SpinLock::new(FileTable::new())),
|
||||
Arc::new(RwLock::new(FileCreationMask::default())),
|
||||
ResourceLimits::default(),
|
||||
Nice::default(),
|
||||
Arc::new(Mutex::new(SigDispositions::default())),
|
||||
|
Reference in New Issue
Block a user