Skip to content

Commit 5494220

Browse files
committed
Merge branch 'vkobinski/master'
2 parents 924c2a1 + dad485f commit 5494220

File tree

14 files changed

+2827
-8
lines changed

14 files changed

+2827
-8
lines changed

Cargo.lock

Lines changed: 1087 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.

crates/benda/Cargo.toml

Lines changed: 19 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,19 @@
1+
[package]
2+
name = "benda"
3+
version = "0.1.0"
4+
edition = "2021"
5+
6+
# See more keys and their definitions at https://doc.rust-lang.org/cargo/reference/manifest.html
7+
[lib]
8+
name = "benda"
9+
crate-type = ["cdylib"]
10+
11+
[dependencies]
12+
pyo3 = { version = "0.21.2", features = [] }
13+
bend-lang = "0.2.33"
14+
num-bigint = "0.4.5"
15+
num-traits = "0.2.19"
16+
rustpython-parser = "0.3.1"
17+
# Bend uses a indexmap to store its ADTs.
18+
# So we need to use this dependency to be able to construct one.
19+
indexmap = "2.2.3"

crates/benda/src/benda_ffi/mod.rs

Lines changed: 20 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,20 @@
1+
use bend::diagnostics::{Diagnostics, DiagnosticsConfig};
2+
use bend::fun::{Book, Term};
3+
use bend::{CompileOpts, RunOpts};
4+
5+
pub fn run(book: &Book) -> Option<(Term, String, Diagnostics)> {
6+
let run_opts = RunOpts::default();
7+
let compile_opts = CompileOpts::default().set_all();
8+
let diagnostics_cfg = DiagnosticsConfig::default();
9+
let args = None;
10+
11+
bend::run_book(
12+
book.clone(),
13+
run_opts,
14+
compile_opts,
15+
diagnostics_cfg,
16+
args,
17+
"run",
18+
)
19+
.unwrap()
20+
}

crates/benda/src/lib.rs

Lines changed: 126 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,126 @@
1+
use bend::imp;
2+
use num_traits::ToPrimitive;
3+
use parser::Parser;
4+
use pyo3::prelude::*;
5+
use pyo3::types::{PyDict, PyFunction, PyString, PyTuple};
6+
use rustpython_parser::{parse, Mode};
7+
use types::extract_type;
8+
use types::tree::{Leaf, Node, Tree};
9+
use types::u24::u24;
10+
mod benda_ffi;
11+
mod parser;
12+
mod types;
13+
14+
#[pyfunction]
15+
fn switch() -> PyResult<String> {
16+
Ok("Ok".to_string())
17+
}
18+
19+
#[pyclass(name = "bjit")]
20+
pub struct PyBjit {
21+
wraps: Py<PyAny>,
22+
}
23+
24+
#[pymethods]
25+
impl PyBjit {
26+
#[new]
27+
fn __new__(wraps: Py<PyAny>) -> Self {
28+
PyBjit { wraps }
29+
}
30+
#[pyo3(signature = (*args, **_kwargs))]
31+
fn __call__(
32+
&self,
33+
py: Python<'_>,
34+
args: &Bound<'_, PyTuple>,
35+
_kwargs: Option<&Bound<'_, PyDict>>,
36+
) -> PyResult<Py<PyAny>> {
37+
let arg_names_temp: Bound<PyAny>;
38+
39+
let (name, filename, arg_names, argcount) =
40+
match self.wraps.downcast_bound::<PyFunction>(py) {
41+
Ok(inner) => {
42+
let name = inner.getattr("__name__").unwrap();
43+
let code = inner.getattr("__code__").unwrap();
44+
let filename = code.getattr("co_filename").unwrap();
45+
46+
arg_names_temp = code.getattr("co_varnames").unwrap();
47+
let arg_names =
48+
arg_names_temp.downcast::<PyTuple>().unwrap();
49+
let argcount = code
50+
.getattr("co_argcount")
51+
.unwrap()
52+
.to_string()
53+
.parse::<u32>()
54+
.unwrap();
55+
56+
(name, filename, arg_names, argcount)
57+
}
58+
Err(_) => todo!(),
59+
};
60+
61+
let mut arg_list: Vec<String> = vec![];
62+
63+
for (index, arg) in arg_names.iter().enumerate() {
64+
if index >= argcount.to_usize().unwrap() {
65+
break;
66+
}
67+
68+
arg_list.push(arg.to_string());
69+
}
70+
71+
let mut parsed_types: Vec<(String, imp::Expr)> = vec![];
72+
73+
for (index, arg) in
74+
args.downcast::<PyTuple>().unwrap().iter().enumerate()
75+
{
76+
parsed_types.push((
77+
arg_list.get(index).unwrap().to_string(),
78+
extract_type(arg).unwrap(),
79+
));
80+
}
81+
82+
let code = std::fs::read_to_string(filename.to_string()).unwrap();
83+
let module = parse(code.as_str(), Mode::Module, "main.py").unwrap();
84+
85+
let mut val: Option<Bound<PyString>> = None;
86+
87+
match module {
88+
rustpython_parser::ast::Mod::Module(mods) => {
89+
for (index, stmt) in mods.body.iter().enumerate() {
90+
if let rustpython_parser::ast::Stmt::FunctionDef(fun_def) =
91+
stmt
92+
{
93+
if fun_def.name == name.to_string() {
94+
let mut parser = Parser::new(
95+
mods.body.clone(),
96+
index,
97+
parsed_types.clone(),
98+
);
99+
let return_val =
100+
parser.parse(fun_def.name.as_ref(), &[]);
101+
val = Some(PyString::new_bound(
102+
py,
103+
return_val.as_str(),
104+
));
105+
break;
106+
}
107+
}
108+
}
109+
}
110+
_ => unimplemented!(),
111+
}
112+
113+
Ok(val.unwrap().into())
114+
}
115+
}
116+
117+
#[pymodule]
118+
fn benda(_py: Python, m: &Bound<'_, PyModule>) -> PyResult<()> {
119+
m.add_function(wrap_pyfunction!(switch, m)?)?;
120+
m.add_class::<PyBjit>()?;
121+
m.add_class::<u24>()?;
122+
m.add_class::<Tree>()?;
123+
m.add_class::<Node>()?;
124+
m.add_class::<Leaf>()?;
125+
Ok(())
126+
}

crates/benda/src/main.rs

Lines changed: 24 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,24 @@
1+
mod parser;
2+
3+
use pyo3::prelude::*;
4+
use rustpython_parser::{parse, Mode};
5+
6+
mod benda_ffi;
7+
8+
fn main() -> PyResult<()> {
9+
let filename = String::from("main.py");
10+
11+
let code = std::fs::read_to_string(filename).unwrap();
12+
let module = parse(code.as_str(), Mode::Module, "main.py").unwrap();
13+
14+
match module {
15+
rustpython_parser::ast::Mod::Module(_mods) => {
16+
//let mut parser = Parser::new(mods.body, 0);
17+
//let val = parser.parse(&String::from("sum_tree"), &["tree".to_string()]);
18+
//println!("Return {:?}", val);
19+
}
20+
_ => todo!(),
21+
}
22+
23+
Ok(())
24+
}

crates/benda/src/parser/builtins.rs

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,3 @@
1+
pub enum BuiltIn {
2+
Switch,
3+
}

0 commit comments

Comments
 (0)