diff --git a/builtin/string.sk b/builtin/string.sk index 9ee38359..37aafb90 100644 --- a/builtin/string.sk +++ b/builtin/string.sk @@ -54,6 +54,10 @@ class String ret end + # Returns list of characters (more specifically, + # grapheme clusters). + #def chars -> Array + # Call `f` for each byte def each_byte(f: Fn1) @bytesize.times do |i| diff --git a/lib/skc_rustlib/src/builtin/array.rs b/lib/skc_rustlib/src/builtin/array.rs index e388a6fb..770c54c8 100644 --- a/lib/skc_rustlib/src/builtin/array.rs +++ b/lib/skc_rustlib/src/builtin/array.rs @@ -1,6 +1,13 @@ -use crate::builtin::{SkInt, SkObj}; -use crate::sk_methods::meta_array_new; -use shiika_ffi_macro::shiika_method; +use crate::builtin::{SkClass, SkInt, SkObj}; +use crate::sk_cls::SkCls; +use shiika_ffi_macro::{shiika_const_ref, shiika_method, shiika_method_ref}; + +shiika_const_ref!("::Array", SkClass, "sk_Array"); +shiika_method_ref!( + "Meta:Array#new", + fn(receiver: SkClass) -> SkAry, + "meta_array_new" +); #[repr(C)] #[derive(Debug)] @@ -16,8 +23,9 @@ struct ShiikaArray { impl SkAry { /// Call `Array.new`. - pub fn new() -> SkAry { - let sk_ary = meta_array_new(std::ptr::null()); + pub fn new() -> SkAry { + let spe_cls = sk_Array().specialize(vec![U::get_class_object()]); + let sk_ary = meta_array_new(spe_cls); // Force cast because external function (Meta_Array_new) // cannot have type a parameter. SkAry(sk_ary.0 as *mut ShiikaArray) diff --git a/lib/skc_rustlib/src/builtin/class.rs b/lib/skc_rustlib/src/builtin/class.rs index 6a277502..98383ee8 100644 --- a/lib/skc_rustlib/src/builtin/class.rs +++ b/lib/skc_rustlib/src/builtin/class.rs @@ -2,9 +2,15 @@ mod witness_table; use crate::builtin::class::witness_table::WitnessTable; use crate::builtin::{SkAry, SkInt, SkStr}; -use crate::sk_methods::meta_class_new; -use shiika_ffi_macro::shiika_method; +use shiika_ffi_macro::{shiika_method, shiika_method_ref}; use std::collections::HashMap; + +shiika_method_ref!( + "Meta:Class#new", + fn(receiver: *const u8) -> SkClass, + "meta_class_new" +); + #[repr(C)] #[derive(Debug)] pub struct SkClass(*mut ShiikaClass); @@ -31,6 +37,10 @@ impl SkClass { unsafe { &(*self.0).name } } + pub fn specialize(self, tyargs: Vec) -> SkClass { + class_specialize(self, tyargs) + } + fn specialized_classes(&mut self) -> &mut HashMap { unsafe { (*self.0).specialized_classes.as_mut().unwrap() } } diff --git a/lib/skc_rustlib/src/builtin/string.rs b/lib/skc_rustlib/src/builtin/string.rs index 4bc3b8cb..32c32e2e 100644 --- a/lib/skc_rustlib/src/builtin/string.rs +++ b/lib/skc_rustlib/src/builtin/string.rs @@ -1,10 +1,18 @@ //! Instance of `::String` use crate::builtin::object::ShiikaObject; -use crate::builtin::{SkAry, SkInt, SkObj, SkPtr}; -use shiika_ffi_macro::shiika_method; +use crate::builtin::{SkAry, SkClass, SkInt, SkObj, SkPtr}; +use crate::sk_cls::SkCls; +use shiika_ffi_macro::{shiika_const_ref, shiika_method}; use std::ffi::CString; use unicode_segmentation::UnicodeSegmentation; +shiika_const_ref!("::String", SkClass, "sk_String"); +impl SkCls for SkStr { + fn get_class_object() -> SkClass { + sk_String() + } +} + extern "C" { // TODO: better name fn gen_literal_string(p: *const u8, bytesize: i64) -> SkStr; diff --git a/lib/skc_rustlib/src/lib.rs b/lib/skc_rustlib/src/lib.rs index 33c0b26f..cc89a90a 100644 --- a/lib/skc_rustlib/src/lib.rs +++ b/lib/skc_rustlib/src/lib.rs @@ -1,3 +1,4 @@ mod allocator; mod builtin; +mod sk_cls; mod sk_methods; diff --git a/lib/skc_rustlib/src/sk_cls.rs b/lib/skc_rustlib/src/sk_cls.rs new file mode 100644 index 00000000..f8f2a920 --- /dev/null +++ b/lib/skc_rustlib/src/sk_cls.rs @@ -0,0 +1,5 @@ +use crate::builtin::SkClass; + +pub trait SkCls { + fn get_class_object() -> SkClass; +}