This commit is contained in:
Graham Kelly 2023-04-12 14:13:26 -04:00
commit 2b5076baa7
8 changed files with 175 additions and 79 deletions

View file

@ -8,7 +8,7 @@
(memory (export "memory") 1) (memory (export "memory") 1)
(func (func
(export "start")(result i32) (export "start")(result i64)
;; Copy into memory the object name ;; Copy into memory the object name
(memory.init 0 (memory.init 0
(i32.const 0) ;; target offset (i32.const 0) ;; target offset
@ -27,10 +27,10 @@
i32.const 5 i32.const 5
call $co call $co
i32.const 6 ;; i32.const 6
i32.const 1 ;; i32.const 1
call $roa ;; call $roa
) )
) )

View file

@ -1,37 +1,50 @@
use core::fmt::{self, Formatter};
use crate::arch::hardware_random_u64; use crate::arch::hardware_random_u64;
use alloc::vec::Vec;
use core::fmt::{self, Formatter};
#[derive(Debug, Eq, Hash, PartialEq, Clone, Copy)]
pub struct OSHandle {
pub id: u64,
}
#[derive(Debug, Eq, Hash, PartialEq)] impl OSHandle {
pub fn new_from_u64(id: u64) -> Self {
Self { id }
}
pub fn random_new() -> Self {
Self {
id: hardware_random_u64(),
}
}
}
#[derive(Debug, Eq, Hash, PartialEq, Clone, Copy)]
pub struct Handle { pub struct Handle {
pub handle_data: i64, id: OSHandle,
perms: Permissions, perms: Permissions,
} }
impl Handle { impl Handle {
pub fn new() -> Handle { pub fn new() -> Handle {
Handle { Handle {
handle_data: hardware_random_u64() as i64, id: OSHandle::random_new(),
perms: Permissions::new(), perms: Permissions::new(),
} }
} }
pub fn as_u64(&self) -> u64 {
self.id.id
}
} }
impl fmt::Display for Handle { impl fmt::Display for Handle {
fn fmt(&self, w: &mut Formatter<'_>) -> Result<(), core::fmt::Error> { fn fmt(&self, w: &mut Formatter<'_>) -> Result<(), core::fmt::Error> {
write!(w, "{}", self.handle_data); write!(w, "{:?}", self.id);
Ok(()) Ok(())
} }
} }
impl Into<i64> for Handle { #[derive(PartialEq, Hash, Eq, Debug, Clone, Copy)]
fn into(self) -> i64 {
self.handle_data
// (abc[0..3] as i64, abc[4..8] as i64)
}
}
#[derive(PartialEq, Hash, Eq, Debug)]
pub struct Permissions { pub struct Permissions {
edit_children: bool, edit_children: bool,
edit_attributes: bool, edit_attributes: bool,

View file

@ -0,0 +1,76 @@
use {
crate::interp::{HFIDT, OBJECTS},
alloc::string::String,
log::trace,
wasmi::{Caller, TypedFunc},
};
use super::{HostState, WasmContext};
pub fn host_register_idt_handler(
caller: Caller<'_, HostState>,
interupt_number: i32,
address_start: i32,
length_of_string: i32,
) -> i32 {
// TODO: get the proc_id to address which function it is
// TODO: Register the function name and proc_id into the idt handler
let mem = caller.get_export("memory").unwrap().into_memory().unwrap();
let mem_array = mem.data(&caller);
let mut name = String::new();
for i in address_start..(address_start + length_of_string) {
let ch = mem_array[i as usize] as char;
name.push(ch);
}
let index = interupt_number as usize;
let hf = HFIDT.lock();
// hf.insert(index);
trace!("{}", name);
0
}
use crate::interp::Handle;
pub fn host_make_object(
mut caller: Caller<'_, HostState>,
address_start: i32,
length_of_string: i32,
) -> i64 {
trace!(
"Called with addr {{ start {} length {} }}",
address_start,
length_of_string
);
let mem = caller.get_export("memory").unwrap().into_memory().unwrap();
let mem_array = mem.data(&caller);
let mut name = String::new();
for i in address_start..(address_start + length_of_string) {
let ch = mem_array[i as usize] as char;
name.push(ch);
}
trace!("Object Name {}", name);
let hand = Handle::new();
{
let binding = OBJECTS;
let mut olock = binding.lock();
let obj = xml::XMLElement::new(name);
olock.push(Some(obj))
}
caller.data_mut().handles.push(hand);
// hand.into()
hand.as_u64().try_into().unwrap()
}
pub type WFIDT = TypedFunc<(), ()>;
fn get_fn_from_wc(wc: WasmContext, function_name: String) -> WFIDT {
wc.instance
.get_typed_func(wc.store, &function_name)
.unwrap()
}

View file

@ -1,11 +1,19 @@
use alloc::string::String; mod host_functions;
use alloc::vec::Vec; mod objects;
use log::trace; use {
use wasmi::Instance; crate::{
use wasmi::{Caller, Func, Linker, Module, Store}; handle::{self, Handle},
use xml::XMLElement; interp::{host_functions::host_make_object, objects::OBJECTS},
},
use crate::handle; alloc::{string::String, vec::Vec},
hashbrown::HashMap,
log::trace,
spin::{Lazy, Mutex},
wasmi::{Caller, Error, Func, Instance, Linker, Module, Store, TypedFunc},
xml::XMLElement,
};
// Seperate use statement
use alloc::vec;
#[derive(Debug)] #[derive(Debug)]
@ -16,8 +24,7 @@ pub struct WasmContext {
} }
pub fn wasm() -> Result<(), wasmi::Error> { pub fn wasm() -> Result<(), wasmi::Error> {
use wasmi::Config; use wasmi::{Config, Engine};
use wasmi::Engine;
let mut conf = Config::default(); let mut conf = Config::default();
conf.wasm_bulk_memory(true); conf.wasm_bulk_memory(true);
// conf., // conf.,
@ -25,12 +32,12 @@ pub fn wasm() -> Result<(), wasmi::Error> {
// trace!("Engine constructed"); // trace!("Engine constructed");
// let wasm = include_bytes!("../../wasm_syscall_test.wasm"); // let wasm = include_bytes!("../../wasm_syscall_test.wasm");
let wasm = include_bytes!("../../test.wasm"); let wasm = include_bytes!("../../../test.wasm");
// trace!("Loading WASM binary"); // trace!("Loading WASM binary");
let module = Module::new(&engine, &wasm[..]).unwrap(); let module = Module::new(&engine, &wasm[..]).unwrap();
// trace!("Constructing wasm module"); // trace!("Constructing wasm module");
let hs = HostState {}; let hs = HostState { handles: vec![] };
let mut store = Store::new(&engine, hs); let mut store = Store::new(&engine, hs);
// trace!("constructing host store"); // trace!("constructing host store");
@ -40,6 +47,7 @@ pub fn wasm() -> Result<(), wasmi::Error> {
); );
let mut linker = <Linker<HostState>>::new(&engine); let mut linker = <Linker<HostState>>::new(&engine);
linker.define( linker.define(
"host", "host",
"read_mem_addr", "read_mem_addr",
@ -51,6 +59,12 @@ pub fn wasm() -> Result<(), wasmi::Error> {
), ),
)?; )?;
linker.define(
"host",
"register_idt_handler",
Func::wrap(&mut store, host_functions::host_register_idt_handler),
)?;
linker.define( linker.define(
"host", "host",
"read_object_attribute", "read_object_attribute",
@ -70,51 +84,24 @@ pub fn wasm() -> Result<(), wasmi::Error> {
let version = instance.get_global(&store, "VERSION"); let version = instance.get_global(&store, "VERSION");
// trace!("Version: {:?}", version); // trace!("Version: {:?}", version);
let hello = instance.get_typed_func::<(), (i32, i32)>(&store, "start")?; let hello = instance.get_typed_func::<(), i64>(&store, "start")?;
let ret = hello.call(&mut store, ())?; let ret = hello.call(&mut store, ())?;
trace!("Called _start got return of {:?}", ret); trace!("Called start got return of {:?}", ret);
Ok(()) Ok(())
} }
#[derive(Clone, Debug)] #[derive(Clone, Debug)]
pub struct HostState {} pub struct HostState {
handles: Vec<Handle>,
}
pub fn read_memory_address(caller: Caller<'_, HostState>, address: i32) -> i32 { pub fn read_memory_address(caller: Caller<'_, HostState>, address: i32) -> i32 {
trace!("Address: {}", address); trace!("Address: {}", address);
// let obj = host_make_object(caller, 16, 23); // let obj = host_make_object(caller, 16, 23);
0 0
} }
use crate::kmain::OBJECTS;
pub fn host_make_object(
caller: Caller<'_, HostState>,
address_start: i32,
length_of_string: i32,
) -> i64 {
trace!(
"Called with addr {{ start {} length {} }}",
address_start,
length_of_string
);
let mem = caller.get_export("memory").unwrap().into_memory().unwrap();
let mem_array = mem.data(&caller);
let mut name = String::new();
for i in address_start..(address_start + length_of_string) {
let ch = mem_array[i as usize] as char;
name.push(ch);
}
trace!("Object Name {}", name);
let hand = handle::Handle::new();
{
let binding = OBJECTS;
let mut olock = binding.lock();
let obj = XMLElement::new(name);
olock.insert(handle::Handle::new(), obj);
}
hand.into()
}
pub fn host_read_object_attribute( pub fn host_read_object_attribute(
caller: Caller<'_, HostState>, caller: Caller<'_, HostState>,
@ -141,8 +128,7 @@ pub fn host_read_object_attribute(
} }
pub fn build_wasm_context(bytes: Vec<u8>) -> Result<WasmContext, wasmi::Error> { pub fn build_wasm_context(bytes: Vec<u8>) -> Result<WasmContext, wasmi::Error> {
use wasmi::Config; use wasmi::{Config, Engine};
use wasmi::Engine;
let mut conf = Config::default(); let mut conf = Config::default();
conf.wasm_bulk_memory(true); conf.wasm_bulk_memory(true);
// conf., // conf.,
@ -150,12 +136,12 @@ pub fn build_wasm_context(bytes: Vec<u8>) -> Result<WasmContext, wasmi::Error> {
// trace!("Engine constructed"); // trace!("Engine constructed");
// let wasm = include_bytes!("../../wasm_syscall_test.wasm"); // let wasm = include_bytes!("../../wasm_syscall_test.wasm");
let wasm = include_bytes!("../../test.wasm"); let wasm = include_bytes!("../../../test.wasm");
// trace!("Loading WASM binary"); // trace!("Loading WASM binary");
let module = Module::new(&engine, &wasm[..]).unwrap(); let module = Module::new(&engine, &wasm[..]).unwrap();
// trace!("Constructing wasm module"); // trace!("Constructing wasm module");
let hs = HostState {}; let hs = HostState { handles: vec![] };
let mut store = Store::new(&engine, hs); let mut store = Store::new(&engine, hs);
// trace!("constructing host store"); // trace!("constructing host store");
@ -200,3 +186,15 @@ pub fn build_wasm_context(bytes: Vec<u8>) -> Result<WasmContext, wasmi::Error> {
Ok(wc) Ok(wc)
} }
pub type HostFunctionIDT = HashMap<usize, WCFunction>;
pub struct WCFunction {
wc: WasmContext,
function: TypedFunc<(), ()>,
}
pub static HFIDT: Lazy<Mutex<HostFunctionIDT>> = Lazy::new(|| {
let mut hfidt = HashMap::new();
Mutex::new(hfidt)
});

View file

@ -0,0 +1,11 @@
use alloc::vec;
use alloc::vec::Vec;
use spin::{Lazy, Mutex};
pub type HostObjects = Vec<Option<xml::XMLElement>>;
pub const OBJECTS: Lazy<Mutex<HostObjects>> = Lazy::new(|| {
let mut obj = vec![];
Mutex::new(obj)
});

View file

@ -2,6 +2,7 @@
// use std::collections::HashMap; // use std::collections::HashMap;
use alloc::vec::Vec;
use log::{info, trace}; use log::{info, trace};
use spin::{Lazy, Mutex}; use spin::{Lazy, Mutex};
@ -44,24 +45,19 @@ pub fn kmain(cmdline: &str, bootstrap: Option<&'static [u8]>) -> ! {
// kcmd.set_attribute("") // kcmd.set_attribute("")
// OBJECTS.lock().insert(hnd, kcmd); // OBJECTS.lock().insert(hnd, kcmd);
// let abc = interp::wasm(); let abc = interp::wasm();
// trace!("{:?}", abc); trace!("{:?}", abc);
let sch = SCHEDULER; // let sch = SCHEDULER;
let mut sch = sch.lock(); // let mut sch = sch.lock();
let wc = interp::build_wasm_context(alloc::vec::Vec::new()).unwrap(); // let wc = interp::build_wasm_context(alloc::vec::Vec::new()).unwrap();
sch.schedule(wc, crate::schedule::ContextWake::None); // sch.schedule(wc, crate::schedule::ContextWake::None);
sch.run(); // sch.run();
// crate::arch::sloop() crate::arch::sloop()
} }
pub const OBJECTS: Lazy<Mutex<HashMap<Handle, xml::XMLElement>>> = Lazy::new(|| {
let mut obj: HashMap<Handle, xml::XMLElement> = HashMap::new();
Mutex::new(obj)
});
use hashbrown::HashMap;
pub const SCHEDULER: Lazy<Mutex<Scheduler>> = Lazy::new(|| { pub const SCHEDULER: Lazy<Mutex<Scheduler>> = Lazy::new(|| {
let mut sch = Scheduler::new(); let mut sch = Scheduler::new();

2
rustfmt.toml Normal file
View file

@ -0,0 +1,2 @@
hex_literal_case = "Upper"
imports_granularity = "One"

BIN
test.wasm

Binary file not shown.