[wip] api messing

This commit is contained in:
Berkus Decker 2021-01-21 12:20:37 +02:00
parent f842a467e4
commit deabc2ae70
1 changed files with 41 additions and 69 deletions

View File

@ -8,54 +8,42 @@
//! Arch-specific kernel ABI decodes syscall invocations and calls API functions to perform actual
//! operations.
use {
vesper_user::SysCall as SysCall,
crate::println,
snafu::Snafu,
crate::arch,
crate::arch::memory::{PhysAddr, VirtAddr},
crate::objects::thread::ThreadState,
crate::caps::{ReplyCapability, NullCapability},
core::result::Result, // temp: use own result type here
crate::platform::rpi3::gic::get_active_irq, // temp: derive based on current platform
crate::objects::thread::TCB,
crate::caps::captable::CapPath,
};
use vesper_user::SysCall as SysCall;
// Syscalls (kernel API)
trait API {
// Three below (send, nb_send, call) are "invocation" syscalls.
// fn send(cap: Cap, msg_info: MessageInfo);
// fn nb_send(dest: Cap, msg_info: MessageInfo);
// fn call(cap: Cap, msg_info: MessageInfo) -> Result<(MessageInfo, Option<&Badge>)>;
fn send(cap: Cap, msg_info: MessageInfo);
fn nb_send(dest: Cap, msg_info: MessageInfo);
fn call(cap: Cap, msg_info: MessageInfo) -> Result<(MessageInfo, Option<&Badge>)>;
// Wait for message, when it is received,
// return object Badge and block caller on `reply`.
// fn recv(src: Cap, reply: Cap) -> Result<(MessageInfo, Option<&Badge>)>;
// fn reply(msg_info: MessageInfo);
fn recv(src: Cap, reply: Cap) -> Result<(MessageInfo, Option<&Badge>)>;
fn reply(msg_info: MessageInfo);
// As Recv but invoke `reply` first.
// fn reply_recv(
// src: Cap,
// reply: Cap,
// msg_info: MessageInfo,
// ) -> Result<(MessageInfo, Option<&Badge>)>;
// fn nb_recv(src: Cap) -> Result<(MessageInfo, Option<&Badge>)>;
// fn r#yield();
fn reply_recv(
src: Cap,
reply: Cap,
msg_info: MessageInfo,
) -> Result<(MessageInfo, Option<&Badge>)>;
fn nb_recv(src: Cap) -> Result<(MessageInfo, Option<&Badge>)>;
fn r#yield();
// -- end of default seL4 syscall list --
// As ReplyRecv but invoke `dest` not `reply`.
// fn nb_send_recv(
// dest: Cap,
// msg_info: MessageInfo,
// src: Cap,
// reply: Cap,
// ) -> Result<(MessageInfo, Options<&Badge>)>;
fn nb_send_recv(
dest: Cap,
msg_info: MessageInfo,
src: Cap,
reply: Cap,
) -> Result<(MessageInfo, Options<&Badge>)>;
// As NBSendRecv, with no reply. Donation is not possible.
// fn nb_send_wait(
// cap: Cap,
// msg_info: MessageInfo,
// src: Cap,
// ) -> Result<(MessageInfo, Option<&Badge>)>;
fn nb_send_wait(
cap: Cap,
msg_info: MessageInfo,
src: Cap,
) -> Result<(MessageInfo, Option<&Badge>)>;
// As per Recv, but donation not possible.
// fn wait(src: Cap) -> Result<(MessageInfo, Option<&Badge>)>;
fn wait(src: Cap) -> Result<(MessageInfo, Option<&Badge>)>;
// Plus some debugging calls...
}
@ -104,20 +92,6 @@ fn handle_syscall(syscall: SysCall) -> Result<()> {
Ok(())
}
fn handle_interrupt(int: u16) -> Result<()> {
Ok(())
}
// some kernel globals
static KernelCurrentThread: &TCB = Default::default(); // @todo Scheduler.CurrentThread
static KernelCurrentFault: Fault = Fault::NoFault;
static KernelSchedulerAction: SchedulerAction = SchedulerAction::None;
static KernelDomainTime: usize = 100; // @todo Scheduler.DomainTime
const msgInfoRegister: usize = 1; // @todo wip number
const capRegister: usize = 2;
const n_MsgRegisters: usize = 2;
// end kernel globals
fn handle_invocation(is_call: bool, is_blocking: bool) -> Result<()> {
let thread: &TCB = KernelCurrentThread;
@ -125,7 +99,7 @@ fn handle_invocation(is_call: bool, is_blocking: bool) -> Result<()> {
let info: MessageInfo = messageInfoFromWord(infoRegister);
let cap_ptr: CapPath = thread.get_register(capRegister);
let result = thread.lookup_cap_and_slot(cap_ptr);
result = thread.lookup_cap_and_slot(cap_ptr);
if result.is_err() {
println!(
@ -201,31 +175,29 @@ fn handle_invocation(is_call: bool, is_blocking: bool) -> Result<()> {
Ok(())
}
fn handle_receive(is_blocking: bool) -> Result<()> {
fn handle_receive(is_blocking: bool) {
let endpoint_cap_ptr = KernelCurrentThread.get_register(capRegister);
let result = KernelCurrentThread.lookup_cap(endpoint_cap_ptr);
if result.is_err() {
// KernelCurrentFault = Fault_CapFault::new(endpoint_cap_ptr, true);
KernelCurrentFault = Fault_CapFault::new(endpoint_cap_ptr, true);
handle_fault(KernelCurrentThread);
return Ok(());
}
match result.capability.get_type() {
endpoint => Ok(()),
notification => Ok(()),
_ => Ok(()), //fault,
match result.cap.get_type() {
endpoint => ,
notification => ,
_ => fault,
}
}
fn handle_reply() {
let caller_slot = KernelCurrentThread.get_caller_slot();
let caller_cap = caller_slot.capability;
const reply_cap = ReplyCapability::Type::Type.value;
const null_cap = NullCapability::Type::Type.value;
match caller_cap.get_type() {
reply_cap => {
ReplyCap::Type.value => {
// if (cap_reply_cap_get_capReplyMaster(callerCap)) {
// break;
// }
@ -233,7 +205,7 @@ fn handle_reply() {
// if(!(caller != ksCurThread)) _assert_fail("caller must not be the current thread", "src/api/syscall.c", 313, __FUNCTION__);
// do_reply_transfer(ksCurThread, caller, callerSlot);
},
null_cap => {
NullCap::Type.value => {
println!("<<vesper[T{} \"{}\" @{}]: Attempted reply operation when no reply capability present.>>", KernelCurrentThread, KernelCurrentThread.name, KernelCurrentThread.get_restart_pc());
},
_ => {
@ -252,8 +224,8 @@ fn handle_yield() {
#[derive(Debug, Snafu)]
enum Fault {
#[snafu(display("no fault"))]
NoFault,
#[snafu(display("null fault"))]
Null,
#[snafu(display("capability fault in {} phase at address {:x}", if in_receive_phase { "receive" } else { "send" }, address))]
Capability {
in_receive_phase: bool,
@ -365,13 +337,13 @@ impl Scheduler {
fn activate_thread() {}
fn dequeue(thread: &mut TCB) {}
fn append(thread: &mut TCB) {}
fn reschedule_required() {}
fn dequeue(thread: &mut TCB);
fn append(thread: &mut TCB);
fn reschedule_required();
}
struct Nucleus {}
// impl API for Nucleus {
impl API for Nucleus {
//...
// }
}