kernel/object/handle/
syscall.rs1use crate::{
6 arch::Trapframe,
7 task::mytask,
8 object::{
9 introspection::KernelObjectInfo,
10 handle::HandleType,
11 handle::StandardInputOutput,
12 handle::HandleMetadata
13 }
14};
15
16pub fn sys_handle_query(trapframe: &mut Trapframe) -> usize {
29 let task = match mytask() {
30 Some(task) => task,
31 None => return usize::MAX,
32 };
33
34 let handle = trapframe.get_arg(0) as u32;
35 let info_ptr = trapframe.get_arg(1);
36
37 trapframe.increment_pc_next(task);
39
40 let info_vaddr = match task.vm_manager.translate_vaddr(info_ptr) {
42 Some(addr) => addr as *mut KernelObjectInfo,
43 None => return usize::MAX, };
45
46 match task.handle_table.get_object_info(handle) {
48 Some(info) => {
49 unsafe {
51 *info_vaddr = info;
52 }
53 0 }
55 None => usize::MAX, }
57}
58
59pub fn sys_handle_set_role(trapframe: &mut Trapframe) -> usize {
70 let task = match mytask() {
71 Some(task) => task,
72 None => return usize::MAX,
73 };
74
75 let handle = trapframe.get_arg(0) as u32;
76 let new_role_raw = trapframe.get_arg(1);
77 let _flags = trapframe.get_arg(2);
78
79 trapframe.increment_pc_next(task);
80
81 let new_role = match decode_handle_type(new_role_raw) {
83 Some(role) => role,
84 None => return usize::MAX, };
86
87 let current_metadata = match task.handle_table.get_metadata(handle) {
89 Some(meta) => meta.clone(),
90 None => return usize::MAX, };
92
93 let new_metadata = HandleMetadata {
95 handle_type: new_role,
96 access_mode: current_metadata.access_mode,
97 special_semantics: current_metadata.special_semantics,
98 };
99
100 if let Err(_) = task.handle_table.update_metadata(handle, new_metadata) {
102 return usize::MAX; }
104
105 0 }
107
108pub fn sys_handle_close(trapframe: &mut Trapframe) -> usize {
119 let task = match mytask() {
120 Some(task) => task,
121 None => return usize::MAX,
122 };
123
124 let handle = trapframe.get_arg(0) as u32;
125 trapframe.increment_pc_next(task);
126
127 if task.handle_table.remove(handle).is_some() {
128 0 } else {
130 usize::MAX }
132}
133
134pub fn sys_handle_duplicate(trapframe: &mut Trapframe) -> usize {
146 let task = match mytask() {
147 Some(task) => task,
148 None => return usize::MAX,
149 };
150
151 let handle = trapframe.get_arg(0) as u32;
152 trapframe.increment_pc_next(task);
153
154 if let Some(kernel_obj) = task.handle_table.get(handle) {
156 match task.handle_table.insert(kernel_obj.clone()) {
158 Ok(new_handle) => new_handle as usize,
159 Err(_) => usize::MAX, }
161 } else {
162 usize::MAX }
164}
165
166fn decode_handle_type(raw: usize) -> Option<HandleType> {
168 match raw {
169 0 => Some(HandleType::Regular),
170 1 => Some(HandleType::IpcChannel),
171 2 => Some(HandleType::StandardInputOutput(StandardInputOutput::Stdin)),
172 3 => Some(HandleType::StandardInputOutput(StandardInputOutput::Stdout)),
173 4 => Some(HandleType::StandardInputOutput(StandardInputOutput::Stderr)),
174 _ => None,
175 }
176}
177
178pub fn encode_handle_type(handle_type: &HandleType) -> usize {
180 match handle_type {
181 HandleType::Regular => 0,
182 HandleType::IpcChannel => 1,
183 HandleType::StandardInputOutput(StandardInputOutput::Stdin) => 2,
184 HandleType::StandardInputOutput(StandardInputOutput::Stdout) => 3,
185 HandleType::StandardInputOutput(StandardInputOutput::Stderr) => 4,
186 }
187}