File tree Expand file tree Collapse file tree 7 files changed +163
-18
lines changed
Expand file tree Collapse file tree 7 files changed +163
-18
lines changed Original file line number Diff line number Diff line change @@ -3,30 +3,35 @@ mod stdlib;
33// ZenLang is not object oriented - therefore it doesn't have classes
44// But you can make something similar
55fn class_new {
6- let inst = {"a" = 0, "b" = 0};
7- return inst;
6+ return {
7+ "add_a" = class_add_a,
8+ "add_b" = class_add_b,
9+ "print" = class_print,
10+ "a" = 0,
11+ "b" = 0
12+ };
813}
914
10- fn class_add_a self n {
15+ fn class_add_a n {
1116 let self.a = self.a + n;
1217 return null;
1318}
1419
15- fn class_add_b self n {
20+ fn class_add_b n {
1621 let self.b = self.b + n;
1722 return null;
1823}
1924
20- fn class_print self {
25+ fn class_print {
2126 let res = self.a + self.b;
2227 println(res);
2328 return null;
2429}
2530
2631fn main {
2732 let class = class_new();
28- class_add_a( class, 42);
29- class_add_b( class, 69);
30- class_print( class);
33+ class.add_a( 42);
34+ class.add_b( 69);
35+ class.print( );
3136 return null;
3237}
Original file line number Diff line number Diff line change 11mod stdlib;
22
33fn stack_new {
4- return {"data" = []};
4+ return {
5+ "top" = stack_top,
6+ "push" = stack_push,
7+ "pop" = stack_pop,
8+ "size" = stack_size,
9+ "is_empty" = stack_is_empty,
10+ "data" = []
11+ };
512}
613
7- fn stack_top self {
14+ fn stack_top {
815 return array_last(self.data);
916}
1017
11- fn stack_push self element {
18+ fn stack_push element {
1219 let self.data = array_push(self.data, element);
1320 return null;
1421}
1522
16- fn stack_pop self {
23+ fn stack_pop {
1724 let self.data = array_pop(self.data);
1825 return null;
1926}
2027
21- fn stack_size self {
28+ fn stack_size {
2229 return array_size(self.data);
2330}
2431
25- fn stack_is_empty self {
26- return stack_size( self) == 0;
32+ fn stack_is_empty {
33+ return self.size( ) == 0;
2734}
2835
2936fn main {
3037 let stack = stack_new();
31- stack_push( stack, 69);
32- println(stack_top( stack));
33- return stack_is_empty( stack);
38+ stack.push( 69);
39+ println(stack.top( ));
40+ return stack.is_empty( );
3441}
Original file line number Diff line number Diff line change @@ -201,3 +201,9 @@ impl Display for Value {
201201 }
202202 }
203203}
204+
205+ impl Default for Value {
206+ fn default ( ) -> Self {
207+ return Value :: Null ( ) ;
208+ }
209+ }
Original file line number Diff line number Diff line change @@ -2,6 +2,7 @@ use crate::strong_u64::U64BitsControl;
22use crate :: value:: * ;
33use crate :: vm:: VM ;
44use alloc:: format;
5+ use alloc:: string:: * ;
56
67impl VM {
78 pub fn op_call ( & mut self ) {
@@ -13,6 +14,11 @@ impl VM {
1314 self . pc . sub_low ( 1 ) ;
1415 self . add_scope ( ) ;
1516
17+ let this_name = & String :: from ( "self" ) ;
18+ let scope = self . scopes . last_mut ( ) . unwrap ( ) ;
19+ scope. create_if_doesnt_exist ( this_name) ;
20+ * scope. get_mut ( this_name) . unwrap ( ) = core:: mem:: take ( & mut self . self_var ) ;
21+
1622 let start = self . bfas_stack_start . pop ( ) . unwrap ( ) ;
1723 let end = self . bfas_stack_end . pop ( ) . unwrap ( ) ;
1824 let diff = end - start;
Original file line number Diff line number Diff line change @@ -19,6 +19,7 @@ impl VM {
1919 self . error = format ! ( "iafs failed: no more values on stack for array" ) ;
2020 return ;
2121 }
22+ self . self_var = array. clone ( ) ;
2223
2324 match array {
2425 Value :: Object ( obj) => match & * obj. borrow ( ) {
Original file line number Diff line number Diff line change @@ -21,6 +21,7 @@ pub struct VM {
2121 pub platform : Option < Box < dyn Platform > > ,
2222 pub global_scope : Scope ,
2323 pub halted : bool ,
24+ pub self_var : Value ,
2425 pub ( crate ) bfas_stack_start : Vec < i64 > ,
2526 pub ( crate ) bfas_stack_end : Vec < i64 > ,
2627}
@@ -38,6 +39,7 @@ impl VM {
3839 platform : None ,
3940 global_scope : Scope :: new ( ) ,
4041 halted : false ,
42+ self_var : Value :: Null ( ) ,
4143 bfas_stack_start : Vec :: new ( ) ,
4244 bfas_stack_end : Vec :: new ( ) ,
4345 } ;
Original file line number Diff line number Diff line change 1+ extern crate alloc;
2+
3+ use zenlang:: compiler:: * ;
4+ use zenlang:: parser:: * ;
5+ use zenlang:: tokenizer:: * ;
6+ use zenlang:: value:: * ;
7+ use zenlang:: vm:: * ;
8+
9+ fn expect_to_return ( code : String , value : Value ) {
10+ let mut tokenizer = Tokenizer :: new ( code) ;
11+ let mut parser = Parser :: new ( & mut tokenizer) ;
12+ let mut compiler = Compiler :: new ( & mut parser) ;
13+ if let Err ( e) = compiler. compile ( ) {
14+ assert_eq ! ( e, "" ) ;
15+ }
16+ let mut vm = VM :: new ( ) ;
17+ let module = compiler. get_module ( ) ;
18+ println ! ( "{:?}" , module. opcodes) ;
19+
20+ let _ = vm. load_module ( & zenlang:: stdlib:: compile_stdlib_module ( ) ) ;
21+ let _ = vm. load_module ( module) ;
22+
23+ if let Err ( e) = vm. set_entry_function ( "main" ) {
24+ assert_eq ! ( e, "" ) ;
25+ }
26+
27+ vm. run_until_halt ( ) ;
28+
29+ println ! ( "vm.ret: {:?}" , vm. ret) ;
30+ assert_eq ! ( vm. error, "" ) ;
31+ assert ! ( vm. ret. equal( & value, & vm) ) ;
32+ }
33+
34+ #[ test]
35+ fn vm_test_self_1 ( ) {
36+ expect_to_return (
37+ r#"
38+ fn f2 {
39+ let self.hi = self.hi + 3;
40+ }
41+
42+ fn f {
43+ let self.hi = 1;
44+ self.test2();
45+ }
46+
47+ fn main {
48+ let obj = {
49+ "test" = f,
50+ "test2" = f2,
51+ };
52+ obj.test();
53+ return obj.hi;
54+ } "#
55+ . into ( ) ,
56+ Value :: Number ( 4.0 ) ,
57+ ) ;
58+ }
59+
60+ #[ test]
61+ fn vm_test_self_2 ( ) {
62+ expect_to_return (
63+ r#"
64+ fn f2 {
65+ let self.hi = 3;
66+ }
67+
68+ fn f {
69+ let self.hi = 1;
70+ let obj = {
71+ "test" = f2
72+ };
73+ obj.test();
74+ let self.hi = obj.hi - 1;
75+ }
76+
77+ fn main {
78+ let obj = {
79+ "test" = f,
80+ };
81+ obj.test();
82+ return obj.hi;
83+ } "#
84+ . into ( ) ,
85+ Value :: Number ( 2.0 ) ,
86+ ) ;
87+ }
88+
89+ #[ test]
90+ fn vm_test_self_3 ( ) {
91+ expect_to_return (
92+ r#"
93+ fn f2 {
94+ let self.hi = 3;
95+ }
96+
97+ fn f {
98+ let self.hi = 1;
99+ let obj = {
100+ "test" = f2
101+ };
102+ obj.test();
103+ let self.hi = obj.hi - 1;
104+ }
105+
106+ fn main {
107+ let obj = {
108+ "obj" = {
109+ "test" = f,
110+ }
111+ };
112+ obj.obj.test();
113+ return obj.obj.hi;
114+ } "#
115+ . into ( ) ,
116+ Value :: Number ( 2.0 ) ,
117+ ) ;
118+ }
You can’t perform that action at this time.
0 commit comments