8
8
extern crate rustpython_parser;
9
9
10
10
use self :: rustpython_parser:: { ast, parser} ;
11
- use super :: super :: obj:: { objdict, objfloat, objint, objlist, objstr, objtuple, objtype} ;
12
- use super :: super :: objbool;
11
+ use super :: super :: obj:: { objstr, objtype} ;
13
12
use super :: super :: pyobject:: {
14
- DictProtocol , PyContext , PyFuncArgs , PyObjectKind , PyObjectRef , PyResult , TypeProtocol ,
13
+ AttributeProtocol , DictProtocol , PyContext , PyFuncArgs , PyObjectRef , PyResult , TypeProtocol ,
15
14
} ;
16
15
use super :: super :: VirtualMachine ;
17
16
@@ -20,31 +19,92 @@ fn program_to_ast(ctx: &PyContext, program: &ast::Program) -> PyObjectRef {
20
19
for statement in & program. statements {
21
20
body. push ( statement_to_ast ( ctx, statement) ) ;
22
21
}
23
- // TODO: create Module node and set attributes:
24
- let ast_node = ctx. new_list ( body) ;
22
+ // TODO: create Module node:
23
+ // let ast_node = ctx.new_instance(this.Module);
24
+ let ast_node = ctx. new_object ( ) ;
25
+ let py_body = ctx. new_list ( body) ;
26
+ ast_node. set_attr ( "body" , py_body) ;
25
27
ast_node
26
28
}
27
29
28
30
fn statement_to_ast ( ctx : & PyContext , statement : & ast:: LocatedStatement ) -> PyObjectRef {
29
- match & statement. node {
30
- ast:: Statement :: FunctionDef { name, args, body } => {
31
- // TODO: create ast.FunctionDef object and set attributes
32
- // let node = ctx.new_object();
31
+ let node = match & statement. node {
32
+ ast:: Statement :: FunctionDef {
33
+ name,
34
+ args : _,
35
+ body,
36
+ } => {
37
+ // TODO: create ast.FunctionDef object:
38
+ let node = ctx. new_object ( ) ;
39
+
40
+ // Set name:
41
+ node. set_attr ( "name" , ctx. new_str ( name. to_string ( ) ) ) ;
42
+
43
+ // Set body:
33
44
let mut py_body = vec ! [ ] ;
34
- py_body. push ( ctx. new_str ( format ! ( "{:?}" , name) ) ) ;
35
- // node.set_attr("name", new_str(name));
36
45
for statement in body {
37
46
py_body. push ( statement_to_ast ( ctx, statement) ) ;
38
47
}
39
48
40
- ctx. new_list ( py_body)
41
- } ,
42
- _ => {
43
- ctx. new_str ( format ! ( "{:?}" , statement) )
49
+ node. set_attr ( "body" , ctx. new_list ( py_body) ) ;
50
+ node
44
51
}
45
- }
52
+ ast:: Statement :: Expression { expression } => {
53
+ let value = expression_to_ast ( ctx, expression) ;
54
+ // TODO: create proper class:
55
+ let node = ctx. new_object ( ) ;
56
+ node. set_attr ( "value" , value) ;
57
+ node
58
+ }
59
+ x => {
60
+ unimplemented ! ( "{:?}" , x) ;
61
+ }
62
+ } ;
63
+
64
+ // set lineno on node:
65
+ let lineno = ctx. new_int ( statement. location . get_row ( ) as i32 ) ;
66
+ node. set_attr ( "lineno" , lineno) ;
67
+
68
+ node
69
+ }
70
+
71
+ fn expression_to_ast ( ctx : & PyContext , expression : & ast:: Expression ) -> PyObjectRef {
72
+ let node = match & expression {
73
+ ast:: Expression :: Call { function, args } => {
74
+ // TODO: create ast.Call instance
75
+ let node = ctx. new_object ( ) ;
76
+
77
+ let py_func_ast = expression_to_ast ( ctx, function) ;
78
+ node. set_attr ( "func" , py_func_ast) ;
79
+
80
+ let mut py_args = vec ! [ ] ;
81
+ for arg in args {
82
+ py_args. push ( expression_to_ast ( ctx, & arg. 1 ) ) ;
83
+ }
84
+ let py_args = ctx. new_list ( py_args) ;
85
+ node. set_attr ( "args" , py_args) ;
86
+
87
+ node
88
+ }
89
+ ast:: Expression :: Identifier { name } => {
90
+ // TODO: create ast.Identifier instance
91
+ let node = ctx. new_object ( ) ;
92
+ let py_name = ctx. new_str ( name. clone ( ) ) ;
93
+ node. set_attr ( "id" , py_name) ;
94
+ node
95
+ }
96
+ ast:: Expression :: String { value } => {
97
+ let node = ctx. new_object ( ) ;
98
+ node. set_attr ( "s" , ctx. new_str ( value. clone ( ) ) ) ;
99
+ node
100
+ }
101
+ n => {
102
+ unimplemented ! ( "{:?}" , n) ;
103
+ }
104
+ } ;
46
105
47
106
// TODO: set lineno on object
107
+ node
48
108
}
49
109
50
110
fn ast_parse ( vm : & mut VirtualMachine , args : PyFuncArgs ) -> PyResult {
@@ -66,5 +126,18 @@ fn ast_parse(vm: &mut VirtualMachine, args: PyFuncArgs) -> PyResult {
66
126
pub fn mk_module ( ctx : & PyContext ) -> PyObjectRef {
67
127
let ast_mod = ctx. new_module ( & "ast" . to_string ( ) , ctx. new_scope ( None ) ) ;
68
128
ast_mod. set_item ( "parse" , ctx. new_rustfunc ( ast_parse) ) ;
129
+ ast_mod. set_item (
130
+ "Module" ,
131
+ ctx. new_class ( & "_ast.Module" . to_string ( ) , ctx. object ( ) ) ,
132
+ ) ;
133
+ // TODO: maybe we can use some clever macro to generate this?
134
+ ast_mod. set_item (
135
+ "FunctionDef" ,
136
+ ctx. new_class ( & "_ast.FunctionDef" . to_string ( ) , ctx. object ( ) ) ,
137
+ ) ;
138
+ ast_mod. set_item (
139
+ "Call" ,
140
+ ctx. new_class ( & "_ast.Call" . to_string ( ) , ctx. object ( ) ) ,
141
+ ) ;
69
142
ast_mod
70
143
}
0 commit comments