Skip to content

Commit 5a74121

Browse files
method
1 parent dd56d1d commit 5a74121

File tree

3 files changed

+31
-15
lines changed

3 files changed

+31
-15
lines changed

vm/src/obj/objfunction.rs

Lines changed: 19 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -29,6 +29,25 @@ impl PyObjectPayload2 for PyFunction {
2929
}
3030
}
3131

32+
#[derive(Debug)]
33+
pub struct PyMethod {
34+
// TODO: these shouldn't be public
35+
pub object: PyObjectRef,
36+
pub function: PyObjectRef,
37+
}
38+
39+
impl PyMethod {
40+
pub fn new(object: PyObjectRef, function: PyObjectRef) -> Self {
41+
PyMethod { object, function }
42+
}
43+
}
44+
45+
impl PyObjectPayload2 for PyMethod {
46+
fn required_type(ctx: &PyContext) -> PyObjectRef {
47+
ctx.bound_method_type()
48+
}
49+
}
50+
3251
pub fn init(context: &PyContext) {
3352
let function_type = &context.function_type;
3453
context.set_attr(&function_type, "__get__", context.new_rustfunc(bind_method));

vm/src/pyobject.rs

Lines changed: 4 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -24,7 +24,7 @@ use crate::obj::objenumerate;
2424
use crate::obj::objfilter;
2525
use crate::obj::objfloat::{self, PyFloat};
2626
use crate::obj::objframe;
27-
use crate::obj::objfunction::{self, PyFunction};
27+
use crate::obj::objfunction::{self, PyFunction, PyMethod};
2828
use crate::obj::objgenerator;
2929
use crate::obj::objint::{self, PyInt};
3030
use crate::obj::objiter;
@@ -666,7 +666,9 @@ impl PyContext {
666666

667667
pub fn new_bound_method(&self, function: PyObjectRef, object: PyObjectRef) -> PyObjectRef {
668668
PyObject::new(
669-
PyObjectPayload::BoundMethod { function, object },
669+
PyObjectPayload::AnyRustValue {
670+
value: Box::new(PyMethod::new(object, function)),
671+
},
670672
self.bound_method_type(),
671673
)
672674
}
@@ -1511,10 +1513,6 @@ pub enum PyObjectPayload {
15111513
Generator {
15121514
frame: PyObjectRef,
15131515
},
1514-
BoundMethod {
1515-
function: PyObjectRef,
1516-
object: PyObjectRef,
1517-
},
15181516
WeakRef {
15191517
referent: PyObjectWeakRef,
15201518
},
@@ -1542,10 +1540,6 @@ impl fmt::Debug for PyObjectPayload {
15421540
PyObjectPayload::Iterator { .. } => write!(f, "iterator"),
15431541
PyObjectPayload::Slice { .. } => write!(f, "slice"),
15441542
PyObjectPayload::Generator { .. } => write!(f, "generator"),
1545-
PyObjectPayload::BoundMethod {
1546-
ref function,
1547-
ref object,
1548-
} => write!(f, "bound-method: {:?} of {:?}", function, object),
15491543
PyObjectPayload::RustFunction { .. } => write!(f, "rust function"),
15501544
PyObjectPayload::Frame { .. } => write!(f, "frame"),
15511545
PyObjectPayload::AnyRustValue { value } => value.fmt(f),

vm/src/vm.rs

Lines changed: 8 additions & 5 deletions
Original file line numberDiff line numberDiff line change
@@ -18,7 +18,7 @@ use crate::frame::{Scope, ScopeRef};
1818
use crate::obj::objbool;
1919
use crate::obj::objcode;
2020
use crate::obj::objframe;
21-
use crate::obj::objfunction::PyFunction;
21+
use crate::obj::objfunction::{PyFunction, PyMethod};
2222
use crate::obj::objgenerator;
2323
use crate::obj::objiter;
2424
use crate::obj::objlist::PyList;
@@ -298,12 +298,15 @@ impl VirtualMachine {
298298
{
299299
return self.invoke_python_function(code, scope, defaults, args);
300300
}
301+
if let Some(PyMethod {
302+
ref function,
303+
ref object,
304+
}) = func_ref.payload()
305+
{
306+
return self.invoke(function.clone(), args.insert(object.clone()));
307+
}
301308
match func_ref.payload {
302309
PyObjectPayload::RustFunction { ref function } => function(self, args),
303-
PyObjectPayload::BoundMethod {
304-
ref function,
305-
ref object,
306-
} => self.invoke(function.clone(), args.insert(object.clone())),
307310
ref payload => {
308311
// TODO: is it safe to just invoke __call__ otherwise?
309312
trace!("invoke __call__ for: {:?}", payload);

0 commit comments

Comments
 (0)