use deimos::vm::dm_type::DmType; use deimos::vm::lib::{DmConstant, DmLib}; use deimos::vm::object_type::{DmField, DmFn, DmImplementation, DmInterface, DmMethod}; use deimos::vm::op_codes::{ add_alloc, add_dealloc, add_invoke_fn, add_mov_const, add_platform_call, add_store, }; use deimos::vm::platform::init_platform_functions; use deimos::vm::{call_fn, DvmContext, DvmState}; use std::rc::Rc; fn main() { // Goal: // - write a single lib with a main() // - call the main fn // fn main() { println "Hello, World!" } // std/core/array lib let mut array_lib = DmLib::new("std/core/array"); // std::core::Array let array_int = DmInterface::new("std::core::Array", "Array"); array_lib.add_interface(array_int); let array_int_rc = array_lib .interfaces() .iter() .find(|interface| interface.fqn() == "std::core::Array") .unwrap(); // std::core::ArrayImpl let mut array_impl = DmImplementation::new( "std::core::ArrayImpl", "ArrayImpl", Some(array_int_rc.clone()), ); let array_impl_ptr_address_fld = DmField::new("ptr_address", DmType::USize); let array_impl_ptr_size_fld = DmField::new("ptr_size", DmType::USize); let array_impl_length_fld = DmField::new("length", DmType::Long); array_impl.add_field(array_impl_ptr_address_fld); array_impl.add_field(array_impl_ptr_size_fld); array_impl.add_field(array_impl_length_fld); // std::core::ArrayImpl::_ctor_0( // r0: self // r1: USize ptr_address // r2: USize ptr_size // r3: Long length // ) let mut array_impl_ctor_0_bytecode: Vec = Vec::new(); add_store(&mut array_impl_ctor_0_bytecode, 0, 0, 1); add_store(&mut array_impl_ctor_0_bytecode, 0, 1, 2); add_store(&mut array_impl_ctor_0_bytecode, 0, 2, 3); let array_impl_ctor_0_fn = DmFn::new( "std::core::ArrayImpl::_ctor_0", "_ctor_0", array_impl_ctor_0_bytecode, 4, None, ); let array_impl_ctor_0_method = DmMethod::new(array_impl_ctor_0_fn, None); array_impl.add_method(array_impl_ctor_0_method); array_lib.add_implementation(array_impl); // std::core::String let mut string_lib = DmLib::new("std/core/string"); let string_int = DmInterface::new("std::core::String", "String"); string_lib.add_interface(string_int); let string_int_rc = string_lib .interfaces() .iter() .find(|interface| interface.fqn() == "std::core::String") .unwrap(); let mut string_impl = DmImplementation::new( "std::core::StringImpl", "StringImpl", Some(string_int_rc.clone()), ); let bytes_field = DmField::new("bytes", DmType::Object); string_impl.add_field(bytes_field); // std::core::String::_ctor_0( // r0: self // r1: Array bytes // ) let mut string_ctor_0_bytecode: Vec = Vec::new(); add_store(&mut string_ctor_0_bytecode, 0, 0, 1); let string_ctor_0_fn = DmFn::new( "std::core::StringImpl::_ctor_0", "_ctor_0", string_ctor_0_bytecode, 2, None, ); let string_ctor_0_method = DmMethod::new(string_ctor_0_fn, None); string_impl.add_method(string_ctor_0_method); string_lib.add_implementation(string_impl); // greeting lib let mut greeting_lib = DmLib::new("greeting"); greeting_lib.add_constant(DmConstant::String("Hello, World!".to_string())); let mut main_byte_code = Vec::new(); // Move greeting // r0: greeting address // r1: greeting size add_mov_const(&mut main_byte_code, 0, 1, "greeting", 0); // Alloc Array greeting bytes add_alloc(&mut main_byte_code, 2, "std::core::ArrayImpl"); // Call ArrayImpl(ptr_address, ptr_size, length) add_invoke_fn( &mut main_byte_code, "std::core::ArrayImpl::_ctor_0", 3, &[2, 0, 1, 1], ); // Alloc StringImpl greeting add_alloc(&mut main_byte_code, 4, "std::core::StringImpl"); // Call StringImpl(greeting_bytes) add_invoke_fn( &mut main_byte_code, "std::core::StringImpl::_ctor_0", 5, &[4, 2], ); // Call println(greeting) add_platform_call(&mut main_byte_code, "std::core::println", 6, &[4]); // Dealloc StringImpl add_dealloc(&mut main_byte_code, 4); // Dealloc ArrayImpl add_dealloc(&mut main_byte_code, 2); let main_dm_fn = DmFn::new("main", "main", main_byte_code, 7, None); greeting_lib.add_function(main_dm_fn); let mut state = DvmState::new(); let mut context = DvmContext::new(); context.load_libs(vec![ Rc::new(greeting_lib), Rc::new(string_lib), Rc::new(array_lib), ]); context.load_platform_fns(init_platform_functions()); let main_fn = context.fn_by_fqn("main").unwrap(); call_fn(&mut state, &context, &main_fn, vec![]); }